1.题目描述
实现函数double Power(double base, int exponent),求base的exponent次方。不得使用库函数,同时不需要考虑大数问题。
示例 1:
输入: 2.00000, 10
输出: 1024.00000
示例 2:
输入: 2.10000, 3
输出: 9.26100
示例 3:
输入: 2.00000, -2
输出: 0.25000
解释: 2-2 = 1/22 = 1/4 = 0.25
说明:
2.思路分析*
利用十进制数字 n的二进制表示,可对快速幂
进行数学化解释。
算法流程:
注意事项(整数越界)
Java代码中,int32变量n∈[-2147483648,2147483647],因此当n=-2147483648时执行n=-n会因越界而赋值出错。解决方法
是现将n存入long变量b,后用b操作即可。
3.正确代码实现
public double myPow(double x,int n) {
if (x==0) {
return 0;
}
long b=n;//把n转为long类型
double res=1.0;
if (b<0) {
x=1/x;
b=-b;
}
while (b>0) {
if ((b&1)==1) res*=x;
b>>=1;
x*=x;
}
return res;
}
4.超时代码(好理解)
private static double myPow1(double x, int n) {
if (n == 0)
return 1;
long b=n;
if (b<0) {
x=1/x;
b=-b;
}
double res = x;// 复制x
int ex = 1;// 令指数为1
// 能翻
while ((ex << 1) <= b) {// 如果指数翻倍后小于目标指数值
// 翻
res = res * res;
// 指数
ex <<= 1;// 指数能翻,那就翻一倍
}
// 不能翻
// 差n-ex次方没有去乘到结果里面
return res * myPow1(x, (int)b - ex);
}
5. 个人想法
这道题核心思想就是把整数转为二进制数字,每处理完一位二进制数,就右移一位,这样就相当于把指数级缩小了一半。
核心代码中while(b>0){},每次都检测二进制数的最后一位,如果是1就与之前的结果相乘,二进制右移,基数翻倍。