• 数论 快速幂的原理讲解


    一. 普通的幂

    二. 快速幂

    三.

      

    (一) 较慢的pow方法 外加 取余。

    用到公式:

    f(x,y) =   f(x,y/2) * f(x,y/2) * x ( y %2 = 1 and y >=1 )

        1 ( y = 0 )

        f(x,y/2) * f(x,y/2) * x ( y %2 = 0 and y >=1 )

    #include <iostream>
    #include <vector>
    #include <stack>
    using namespace std;
        int t;
        int x,y,p;
    long long pow(long long x,long long y){
        if(y<=0)
            return 1;
        else if(y%2 == 1)
            return (pow(x,y/2)*pow(x,y/2)*x)%p;
        else if(y%2 == 0)
            return (pow(x,y/2)*pow(x,y/2))%p;
    }
    typedef long long ll;
    ll pow(ll a,ll b){
        ll ans = 1,base = a;
        
    }
    
    int main(){
    
        cin >> t;
        for(int i=0;i<t;++i){
            cin >> x >> y >> p;
        }
        cout << pow(x,y) % p << endl;;
        return 0;
    }

     

    (二) 那么快速幂是什么? 为什么要用到快速幂?

    原因:快

      普通pow的时间复杂度是 O(n),而快速幂 的时间复杂度为 O( logn)

    假如我们求 XY ,

      当 Y = 8 的时候。

      X8 = X (2^3)

    8的二进制:

      8(2) = 1000 = 1 *2^3 + 0 *2^2 + 0 *2^1 + 0 *2^0

    那么

      XY = X (2^3) = X(1 *2^3 + 0 *2^2 + 0 *2^1 + 0 *2^0 )

       = 1*  X2^3 + 0*  X2^2 + 0*  X2^1 + 0*  X2^0

       = 1*  (((X2^0)2)2)2  + 0* ( (X2^0)2)2 + 0*(X2^0)2 + 0*  X2^0 

          = 1*  (((X)2)2)2  + 0* ( (X)2)2 + 0*(X)2 + 0*  X

     

    代码就可以写出。

    ll pow(ll x,ll y){
        ll ans = 1,base = x;
        while(y){
            if(y % 2 == 1){
                ans = ans * base;
            }
            base = base * base;
            y/=2;
        }
        return ans;
    }

     

    用位运算优化一下,

    得出模板。

    typedef long long ll;
    ll pow(ll x,ll y){
        ll ans = 1,base = x;
        while(y){
            if(y&1 != 0){
                ans *= base;
            }
            base *= base;
            y >>= 1;
        }
        return ans;
    }

     

    如果要加上 取余运算 那么。

    typedef long long ll;
    ll pow(ll x,ll y){
        ll ans = 1,base = x;
        while(y){
            if(y&1 != 0){
                ans = (ans%p * base%p)%p;
            }
            base = (base%p * base%p) %p;
            y >>= 1;
        }
        return ans;
    }

     

    题目:

    牛客 C-King

    链接:https://ac.nowcoder.com/acm/contest/554/C
    来源:牛客网
    
    题目描述 
    国王有一块神奇土地
    第一天可以产a吨粮食,第二天会变成前一天的a倍,以此类推。
    n天后大臣准备把这些粮食尽可能多的平均分给b个城池
    为了方便,每个城池分到的粮食都是整吨整吨哒!
    剩下的粮食国王准备贪污
    国王能贪到多少吨粮食呢?
    
    输入描述:
    输入的第一行为一个数字T(T<=100),表示数据输入的组数。
    之后每行3个数字,分别表示 a, n, b(1<=a,n<= 1000,000,000;1<=b<=1000 )。
    输出描述:
    对于每组数据输出对应结果
    示例1
    输入
    复制
    1
    2 2 3
    输出
    复制
    1
    View Code

    代码:

    #include <iostream>
    using namespace std;
    long long pow(long long a,long long b,long long n){
        long long base = a;
        long long ans = 1;
        while(b){
            if(b&1){
                ans = (ans%n * base%n)%n;
            }
            base = (base%n *base%n)%n;
            b>>=1;
        }
        return ans;
    }
    int main(){
        int T;
        cin >> T;
        long long a,n,b;
        while(T--){
            cin >> a >> n >> b;
            cout << pow(a,n,b) << endl;
        }
        return 0;
    }
    View Code
  • 相关阅读:
    Linux免密登录
    HDFS shell 常用命令
    zabbix4.4图表中文显示乱码解决办法
    安装zabbix-agent
    安装配置zabbix4.4
    elasticsearch插件sql安装
    dedecms调用头部文件 dede:include时页面出现一行空白的解决方案
    DedeCMS <=5.7 SP2 file_class.php 任意文件上传漏洞
    DedeCMS后台文件任意上传漏洞media_add.php的修改方法
    织梦DEDECMS任意文件上传漏洞与注入漏洞修复方法
  • 原文地址:https://www.cnblogs.com/--zz/p/10479968.html
Copyright © 2020-2023  润新知