这是【六分钟学算法】的第一季,剑指offer系列,作者将利用十五天时间C++实现,带你玩转算法,剑指offer,喜欢的话可以点赞关注+收藏,每日更新中ing。
题目15. 数值的整数次方
实现函数 double Power(double base, int exponent)
,求base的 exponent次方。
不得使用库函数,同时不需要考虑大数问题。
只要输出结果与答案的绝对误差不超过 10^−2 即视为正确。
注意:
- 不会出现底数和指数同为0的情况
- 当底数为0时,指数一定为正
- 底数的绝对值不超过 10,指数的绝对值不超过 109。
样例1
输入:10 ,2
输出:100
样例2
输入:10 ,-2
输出:0.01
【题解】-- 模拟
模拟算法是一种最基本的算法思想 ,是对程序员基本编程能力的一种考查,其解决方法就是根据题目给出的规则对题目要求的相关过程进行编程模拟。在解决模拟类问题时,需要注意字符串处理、特殊情况处理和对题目意思的理解。我们知道在C语言中,通常使用函数srand()
和rand()
来生成随机数。
其中函数srand()
用于初始化随机数发生器,然后使用函数rand()
来生成随机数。如果要使用上述两个函数,则需要在源程序头部包含time.h文件。在程序设计过程中,可使用随机函数来模拟自然界中发生的不可预测情况。
在解题时,需要仔细分析题目给出的规则,要尽可能地做到全面地考虑所有可能出现的情况,这是解模拟类问题的关键点之一。可以根据以下的实例来理解此算法:
// 模拟猜数字游戏
#include <time.h>
#include <stdio.h>
int main()
{
int n,m,i=0;
int max=100,min=1;//用于比较数字范围
srand(time(NULL));//初始化随机数发生器
n=rand() % 100 + 1;//产生1到100的随机数
do{
printf("%d<目标数<%d哦!输入你猜的数字:",min,max);
scanf("%d",&m);
i++;//统计猜数字的次数
if (m>n)
{
printf("您所猜的数字太大了!\n");
max = m;//刷新最大值
}
else if(m<n)
{
printf("您所猜的数字太小了!\n");
min = m;//刷新最小值
}
}while(m!=n);
printf("回答正确!\n");
printf("共猜测了%d次。\n",i);
if(i<=5)
printf("你太聪明了,这么快就猜出来了!\n");
else if(i>5)
printf("还需改进方法,以便更快猜出来!呵呵\n");
return 0;
}
由于本题的指数是int范围,可能很大,所以需要用快速幂求解。
注意当指数是负数时,我们需要先取指数的绝对值,最后将乘积的倒数作为答案。
复杂度分析:
假设指数是 n,则一共会循环 O(logn)次,所以时间复杂度是 O(logn)。
C++代码实现:
class Solution {
public:
double myPow(double x, int n) {
typedef long long LL;
bool is_minus = n < 0;
double res = 1;
for (LL k = abs(LL(n)); k; k >>= 1) {
if (k & 1) res *= x;
x *= x;
}
if (is_minus) res = 1 / res;
return res;
}
};