Num 16: HDOJ: 题目1061 : Rightmost Digit [ 求个位数 ] [ 快速幂算法 ]
来源:互联网 发布:客户地图软件 编辑:程序博客网 时间:2024/06/11 20:41
题目:
Rightmost Digit
Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65536/32768 K (Java/Others)Total Submission(s): 39386 Accepted Submission(s): 14861
Each test case contains a single positive integer N(1<=N<=1,000,000,000).
234
76HintIn the first case, 3 * 3 * 3 = 27, so the rightmost digit is 7.In the second case, 4 * 4 * 4 * 4 = 256, so the rightmost digit is 6.
刚看到题的时候就应该意识到,一定不能强行计算 N^N%10 然后输出,计算量大,而且会数据溢出;
大数乘法在这里也不太合适,毕竟要算N次方,就算计算出来,submit 的时候也不能够保证不超时;
所以感觉到应该是有内在规律,仔细研究后发现:
1.
在计算 N^N 的个位数的时候,个位数的数值仅与N的个位数有关;
所以可以利用计算( N%10 )^N 的个位数来代替原题;
2.
进一步的,演算后发现1-9的N( N>0 )次方按4个数一循环;
例:3的1-9次方的个位数依次为 ( 3, 9,7,1,3,9,7,1,3) ;
所以对于次方数也可以做简化,次方为:N%4 ;
这里要注意,当N%4==0的时候N应当取4;( 否则X^0=1,只会输出1 )
通过以上的分析,我们就将问题转化为求 ( N%10 )^( N%4 )的个位数的问题了;
大大简化了计算过程,而且保证了数据一定不会溢出;
AC代码:
<span style="font-size:18px;">#include<stdio.h>#include<math.h>int main(){int t;scanf("%d",&t);while(t--){int n,num,index;scanf("%d",&n);num=n%10;index=n%4;if(index==0) index=4;printf("%d\n",(int)(pow((double)num,index))%10);}return 0;}</span>
注意:pow函数的格式pow( double x, int index ),要学会利用类型的强制转换;
见网上也有许多人在说用快速幂的方法也可以做;
这里仅介绍快速幂算法,不推荐在这道题上使用快速幂的方法;
快速幂:
分为二分法和位运算( 位操作 );
原理:
例如在计算 2^4 的时候,当计算过 2^2后, 可以直接计算 ( 2^2 )^2即可;
1.二分法:
<span style="font-size:18px;">#include<stdio.h>int pow2(int a,int b)// a:底数 b:指数{ int r=1,base=a;while(b!=0){ if(b%2) r*=base; // 如果次方为奇数,r乘一个底数( 使次方变为偶数 ); base*=base; // 每计算循环一次,底数所乘的数都为上一次的平方倍,减少次数; b/=2;} return r;}int main(){ int a,b; while (scanf("%d%d",&a,&b)) printf("%d\n",pow2(a,b));}</span>
2.位运算:
原理和二分法相似,只不过是通过位运算来对数据做处理的;
<span style="font-size:18px;">#include<stdio.h>int pow3(int a,int b){int r=1,base=a;while(b!=0){if(b&1)r*=base;base*=base;b>>=1;}return r;}int main(){ int a,b; while (scanf("%d%d",&a,&b)) printf("%d\n",pow3(a,b));}</span>
我们也可以用计算快速幂的方法来进行余数的计算( 求个位数即对10取余 ):
这里用到的方法为:
快速幂取模算法:
利用离散数学之中所讲的知识,我们有公式:
( a^b ) mod c=( a mod c )^b mod c ;
通过数学知识,我们可化简此等式有( 可循环[ 递归 ]计算 ):
奇数时:(a mod c) * ( a^2 mod c)^( b/2 ) mod c ;
偶数时: a^2 mod c)^( b/2 ) mod c ;
所以在计算 N^N 的个位数的时候,解决了 N^N可能太大存不下的问题,也减少了步数:
<span style="font-size:18px;">#include<stdio.h>int powermod(int a, int b, int c){ int rest=1; a=a%c;//公式中的( a mod c ) while(b>0)//类似于二分法分步求余 { if(b%2==1) rest=(rest*a)%c; b=b/2; a=(a*a)%c; } return rest;}int main(){int base,index,rest;while(scanf("%d%d%d",&base,&index,&rest)) printf("%d\n",powermod(base,index,rest));}</span>
函数用于 a^b%c 的快速计算 ;
- Num 16: HDOJ: 题目1061 : Rightmost Digit [ 求个位数 ] [ 快速幂算法 ]
- ACM--快速幂--HDOJ 1061--Rightmost Digit
- HDOJ 1061 Rightmost Digit(快速幂)
- HDU 1061 Rightmost Digit 【快速求幂】
- HDOJ 题目1061Rightmost Digit(数学)
- HDOJ 题目1061Rightmost Digit(规律)
- HDOJ 1061 Rightmost Digit(快速幂求模)
- HDU 1061 Rightmost Digit(快速幂题目)
- HDU 1061 Rightmost Digit (四则运算求余,快速幂)
- HDOJ 1061: Rightmost Digit
- hdoj 1061Rightmost Digit
- HDOJ 1061 Rightmost Digit
- HDOJ 1061 Rightmost Digit
- hdoj 1061 Rightmost Digit
- HDOJ 1061 - Rightmost Digit
- HDOJ--1061--Rightmost Digit
- HDOJ 1061Rightmost Digit
- HDOJ 1061 Rightmost Digit
- Petrel 2014 图形工作站应用方案
- linux内核分析笔记----中断和中断处理程序
- Algorithms—61.Rotate List
- Oracle 列转行函数 Listagg()示例
- ftp error "425 Use PORT or PASV first."
- Num 16: HDOJ: 题目1061 : Rightmost Digit [ 求个位数 ] [ 快速幂算法 ]
- Android利用Fiddler进行网络数据抓包
- 返回函数的JavaScript函数
- Android笔记之:App模块化及工程扩展的应用
- Java安全(加密、摘要、签名、证书、SSL、HTTPS)
- Android 开发之:Intent.createChooser() 妙用
- 关于APPIcon
- 【工具】applicationContext.xml文件放在src下
- 数据挖掘的数据集资源