poj1845 Sumdiv
2012-05-27 14:25
232 查看
题意:求A^B的值的所有因子的和模9901,例如2^3=8 => 1+2+4+8=15。最后答案为 15。
分析:先将A^B分解成素因数形式:A^B = (P1^k1) + (P2^k2) + (P3^k3) + ...
那么A^B所有因子之和就是:S = (1 + P1^1 + P1^2 + P1^3 +...+ P1^K) * (1 + P2^1 + P2^2 + P2^3+...+P2^K) * (1 + P3^1 + P3^2 + P3^3 +...+ P3^K) * (...
计算 1 + P + P^2 + P^3 +...+ P ^K 可用二分求解;
当k是偶数时:例如k=4,1 + P + P^2 + P^3 + P^4 = (1+P) + P^2 * (1+P*(1+P));
当k是奇数时:例如k=5,1 + P + P^2 + P^3 + P^4 + P^5 = (1 + P + P^2) + P^3 * (1 + P + P^2)
分析:先将A^B分解成素因数形式:A^B = (P1^k1) + (P2^k2) + (P3^k3) + ...
那么A^B所有因子之和就是:S = (1 + P1^1 + P1^2 + P1^3 +...+ P1^K) * (1 + P2^1 + P2^2 + P2^3+...+P2^K) * (1 + P3^1 + P3^2 + P3^3 +...+ P3^K) * (...
计算 1 + P + P^2 + P^3 +...+ P ^K 可用二分求解;
当k是偶数时:例如k=4,1 + P + P^2 + P^3 + P^4 = (1+P) + P^2 * (1+P*(1+P));
当k是奇数时:例如k=5,1 + P + P^2 + P^3 + P^4 + P^5 = (1 + P + P^2) + P^3 * (1 + P + P^2)
#include <iostream> #include <fstream> #include <cstdio> #include <algorithm> #include <cstring> #include <vector> #include <bitset> #include <cmath> #include <queue> #include <stack> #include <set> #include <map> #include <ctime> #define LL long long #define Vi vector<int> #define Si set<int> #define readf freopen("input.txt","r",stdin) #define writef freopen("output.txt","w",stdout) #define FU(i,a) for(int i(1); i <= (a); i++) #define FD(i,a) for(int i(a); i >= (1); i--) #define FOR(i,a,b) for(int i(a);i <= (b); i++) #define FORD(i,a,b) for(int i(a);i >= (b); i--) #define SET(a,b) memset(a,b,sizeof(a)) #define SD(a) scanf("%d",&(a)) #define LN printf("\n") #define PS printf(" ") #define pb push_back #define lson l , m , rt << 1 #define rson m + 1 , r , rt << 1 | 1 const double pi = acos(-1.0); const int maxn = 10001; const int INF=99999999; using namespace std; int A,B; int M = 9901; LL pow(LL a,LL exp){ LL ret=1,s=a%M; while(exp){ if(exp&1) ret=(ret*s)%M; exp>>=1; s=(s*s)%M; } return ret; } LL sum(LL p,LL n){//求1 + p + p^2 +...+ p^n; if(n==0) return 1; if(n & 1) //n % 2 == 0; return (((1 + pow(p,n/2+1)) % M) * (sum(p,n/2) % M)) % M; else return (((1 + pow(p,n/2+1)) % M) * (sum(p,(n-1)/2) % M) + pow(p,n/2) % M) % M; } int main(){ LL s, ans; int i, p[maxn], c[maxn]; //p[i]表示第i个素因子,c[i]表示它的个数。 while(scanf("%d%d",&A,&B)!= EOF){ memset(p, 0, sizeof(p)); memset(c, 0, sizeof(c)); //a^b=p1^(c1*b) * .... * pi^(ci*b) //ans=(1+p1+p1^2+...+p1^(c1*b))*()...*(1+pi+pi^2+...+pi^(ci*b)) //把A分解素数 for(i=2; i*i<=A; i++){//求所有A的素因子存在p[]中, if(A % i ==0){ p[++p[0]] = i; while( A % i == 0){ A /= i; ++c[p[0]]; //对应的素因子的个数。 } } } if( A != 1){ //处理最后一个数。 p[++p[0]] = A; c[p[0]] = 1; } ans = 1; for(i=1; i<=p[0]; i++)//sum=(p1^(n1*B+1)–1)/(p1-1)*(p2^(n2*B+1)–1)/(p2–2)*… ans = ((ans % M) * (sum(p[i], c[i]*B)) % M) % M; printf("%lld\n",ans); } return 0; }
相关文章推荐
- POJ 1845 Sumdiv(因子分解+快速幂+二分求和)
- poj 1845 Sumdiv (很多数论知识 ,很经典 )
- POJ1845 Sumdiv(求所有因数和+矩阵快速幂)
- POJ 1845:Sumdiv 快速幂+逆元
- POJ_1845_Sumdiv_各种数学
- POJ 1845 Sumdiv【同余模运算+递归求等比数列和+快速幂运算】
- poj 1845 Sumdiv
- POJ1845 Sumdiv
- POJ 1845 Sumdiv(质因数分解+快速幂+二分法求等比数列的和)
- POJ 1845 Sumdiv
- POJ 1845-Sumdiv【经典数学题目---求因子和】
- poj1845--Sumdiv(数论篇3--真滴是数论啊。。。。)
- POJ 1845 Sumdiv 【推公式 | 逆元】
- POJ 1845 - Sumdiv
- poj 1845 Sumdiv
- poj1845 Sumdiv
- poj 1845 Sumdiv (算术基本定理求一个数因子和)
- poj_1845 Sumdiv(素因子分解+快速幂+约数和+二分求等比数列和)
- poj 1845 sumdiv
- POJ-1845-Sumdiv