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

快速幂运算(非大数)

时间:2015-08-30 22:49:55      阅读:158      评论:0      收藏:0      [点我收藏+]

标签:

快速幂顾名思义,就是快速算某个数的多少次幂。其时间复杂度为 O(log?N), 与朴素的O(N)相比效率有了极大的提高。

 

下面以3­16 为例:

 

一般运算方式是:

316 = 3*3*3*3……*3

这样的话需要运算15次

 

而快速幂运算的方式是:

316 = (32)8 = ((32)2)4 = (((32)2)2)2

这样的话只需要运算4次

 

不难看出,快速幂运算其实就是每次运算时把底数平方,指数减半,从而提高效率。

 

显然,当指数为奇数时,我们要作一些特殊处理:

以711为例:

711 = 710 * 7 = (72)5 * 7 = (72)4 * 72 * 7 = ((72)2)2 * 72 * 7

其实与前面的运算差异不大,当指数为奇数时,只需要从指数里取出1来单独运算即可。

 

以下为递归实现快速幂代码:

 1 #include <stdio.h>
 2 typedef long long int LL; //为long long int 定义别名 LL
 3 LL FastPower(LL a, LL b, LL c) //a为底数,b为指数,c用来存储单独运算的乘积
 4 {
 5     if(b == 0) //任何数的0次方都为1(0的0次方有争议,这里默认为1)
 6         return 1;
 7     else if(b == 1) //递归出口
 8         return a*c; //运算结束,返回结果
 9     else if(b%2 == 1) //当指数为奇数时
10         return FastPower(a*a, (b-1)/2, c*a); //从指数取出1来乘到c里存储起来,其他照常
11     else //当指数为偶数
12         return FastPower(a*a, b/2, c);
13 }
14 int main(void)
15 {
16     LL a, b;
17     //测试
18     while(~scanf("%lld %lld", &a, &b))
19         printf("%lld^%lld = %lld\n\n", a, b, FastPower(a, b, 1)); //c的初始值应为1而不是0
20     return 0;
21 }

运用上位运算稍微优化一下代码

 1 #include <stdio.h>
 2 typedef long long int LL;
 3 LL QPower(LL a, LL b, LL c)
 4 {
 5     if(!b)
 6         return 1;
 7     else if(b == 1)
 8         return a*c;
 9     else
10         return b&1 ? QPower(a*a, b-1>>1, a*c) : QPower(a*a, b>>1, c);
11 }
12 int main(void)
13 {
14     LL a, b;
15     while(~scanf("%lld %lld", &a, &b))
16         printf("%lld\n", QPower(a, b, 1));
17     return 0;
18 }

如有错误,欢迎指出

快速幂运算(非大数)

标签:

原文地址:http://www.cnblogs.com/gwtan/p/4771689.html

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