码迷,mamicode.com
首页 > 其他好文 > 详细

数论--快速幂,矩阵快速幂

时间:2017-10-03 20:38:49      阅读:197      评论:0      收藏:0      [点我收藏+]

标签:例题   int   pow   二进制   str   blog   ...   return   bsp   

1.快速幂:

当求a的b次方的时候,我们可以写一个函数一次循环求出,又可以用math文件里面的pow(double a,double b)解决

但是,当b非常大还要取模呢?O(n)的时间复杂度也不行怎么办?

可以用快速幂的方法:

要求a^b时,那么其实b是可以拆成二进制的,该二进制数第i位的权为2^(i-1),例如当b==11时

             a^11=a^(2^0+2^1+2^3)=a^(2^0)*a^(2^1)*a^(2^3)

实现时要用到位运算:

b&1是取b二进制的末尾

b>>1是去掉b二进制的末尾

 1 #include<cstdio>
 2 #include<iostream>
 3 using namespace std;
 4  
 5 #define ll long long 
 6  
 7 ll pow_mod(ll a,ll b,ll p)  //(a^b)%p 
 8 {
 9      ll ans=1;
10      while(b)
11      {
12          if(b&1)
13          {
14              ans=(ans*a)%p;
15          }
16          a=(a*a)%p;
17          b>>=1;
18      }
19      return ans;
20  }
21  
22  
23  int main()
24  {
25      ll a,b,p;
26      cin>>a>>b>>p;
27      cout<<pow_mod(a,b,p)<<endl;  
28  }

 

其中,a=(a*a)%p理解起来就是:第0次a=a^(2^0);//初始值 ,第一次a=a*a相当于a^(2^1),第二次相当于a^(2^2).......a^(2^n),再结合上面a^11=a^1011(二进制)=a^(2^0)*a^(2^1)*a^(2^3),

对应的就是,在第0次,第1次,第3次的时候,ans=(ans*a)%p;

而在第0次,第1次,第3次的时候ans要更新,是因为11的二进制1011的第0位,第1位,第3位是1(即if(b&1),当前b的末尾是1)

讲解over,例题POJ 1995

 

2.矩阵快速幂:

 

数论--快速幂,矩阵快速幂

标签:例题   int   pow   二进制   str   blog   ...   return   bsp   

原文地址:http://www.cnblogs.com/eastblue/p/7624370.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!