hdu 2421简单数论题
读不懂题目的孩子伤不起啊~~~~~~~这题我第一次理解为n的所有约数的立方和,打完一看,样例都不对。。。再读读题,以为是求出n的约数个数x,然后求1^3+2^3+3^3+...+x^3,打完了也能过样例,交上去却WA。。。无奈只好翻别人的解题报告看,才明白题目的意思是求g(n)=∑f(d)^3 (d|n,f(n)表示n的约数个数)
易证g(n)为积性函数,即若gcd(n,m)=1则g(nm)=g(n)*g(m)。所以对n分解素因数后N=p1^a1 * p2^a2 ……pj^aj,则可得g(n)=g(p1^a1)*……g(pj^aj)。
而对于每个g(p1^a1)=1^3+……(a1+1)^3=(a1+1)^2*(a1+2)^2 /4。依此思路,不难解出本题。
/* * hdu2421/win.cpp * Created on: 2012-11-2 * Author : ben */ #include <cstdio> #include <cstdlib> #include <cstring> #include <cmath> #include <ctime> #include <iostream> #include <algorithm> #include <queue> #include <set> #include <map> #include <stack> #include <string> #include <vector> #include <deque> #include <list> #include <functional> #include <numeric> #include <cctype> using namespace std; const int MOD = 10007; const int _4MOD = 4 * MOD; typedef long long LL; typedef vector<pair<int, int> > Int_Pair; void get_prime_table(int N, vector<int> &pt) { vector<bool> ip; ip.resize(N + 1); fill(ip.begin(), ip.end(), true); int i, j, s, t = N - 1; for (i = 3; i <= N; i++) { s = (int) sqrt(i); for (j = 2; j <= s; j++) { if (i % j == 0) break; } if (j <= s) { ip[i] = false; t--; } } pt.resize(t); t = 0; for(int i = 2; i <= N; i++) { if(ip[i]) { pt[t++] = i; } } } void get_prime_factor(int N, Int_Pair &f, const vector<int> &p) { int i, t, n, pl = p.size(); f.clear(); for(i = 0; i < pl; i++) { t = p[i]; if(N % t == 0) { n = 0; while(N % t == 0) { n++; N /= t; } f.push_back(make_pair(t, n)); } if(N == 1) { break; } } if(N > 1) { f.push_back(make_pair(N, 1)); } } int main() { #ifndef ONLINE_JUDGE freopen("data.in", "r", stdin); #endif vector<int> prime_table; get_prime_table(2000, prime_table); int A, B, t = 1, n, ans; LL temp; while(scanf("%d%d", &A, &B) == 2) { Int_Pair ip; get_prime_factor(A, ip, prime_table); ans = 1; for(int i = 0, len = ip.size(); i < len; i++) { n = (ip[i].second * (LL)B + 1) % _4MOD; temp = ((n * n) % _4MOD) * (((n + 1) * (n + 1)) % _4MOD); temp = (temp % _4MOD) / 4; ans *= temp; ans %= MOD; } printf("Case %d: %d\n", t++, ans); } return 0; }