poj 2480最大公约数和

我校OJ1110题跟poj2480题目是一样的,最大公约数和,思路挺简单,就是求出n的所有约数pi,然后f(n) = Σ(pi*Φ(n/pi))。代码打得挺乱的,POJ上1Y了,可本校OJ死活过不了,TLE,竹子出题真是变态啊,有空再优化吧,先贴个代码。

/*
 * poj2480/win.cpp
 * Created on: 2012-9-27
 * 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;
typedef long long LL;
const int MAXP = 5000;
int primenum, primes[MAXP];
int pflen, primefactor[50], primefactornum[50];

int getPhi(int n) {
    int i, te, phi;
    te = (int) sqrt(n * 1.0);
    for (i = 2, phi = n; i <= te; i++)
        if (n % i == 0) {
            phi = phi / i * (i - 1);
            while (n % i == 0) {
                n /= i;
            }
        }
    if (n > 1) {
        phi = phi / n * (n - 1);
    }
    return phi;
}

void getPrimeFactor(int n) {
    memset(primefactornum, 0, sizeof(primefactornum));
    pflen = 0;
    int s = (int) sqrt(n);
    for(int i = 0; i < primenum && primes[i] <= s; i++) {
        if(n % primes[i] == 0) {
            primefactor[pflen] = primes[i];
            while(n % primes[i] == 0) {
                n /= primes[i];
                primefactornum[pflen]++;
            }
            pflen++;
        }
    }
    if(n > 1) {
        primefactor[pflen] = n;
        primefactornum[pflen] = 1;
        pflen++;
    }
}

void init_prime_table(int N) {
    int i, j, s;
    primes[0] = 2;
    primenum = 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) {
            primes[primenum++] = i;
        }
    }
}

void dfs(int data[], int now, stack<int> &S) {
    if(now >= pflen) {
        int num = 1;
        for(int i = 0; i < pflen; i++) {
            for(int j = 0; j < data[i]; j++) {
                num *= primefactor[i];
            }
        }
        S.push(num);
        return ;
    }
    data[now] = 0;
    for(; data[now] <= primefactornum[now]; data[now]++) {
        dfs(data, now + 1, S);
    }
}

LL work(int N) {
    getPrimeFactor(N);
    stack<int> S;
    int data[50];
    dfs(data, 0, S);
    LL res = 0;
    while(!S.empty()) {
        int t = S.top();
        res += (LL)t * getPhi(N / t);
        S.pop();
    }
    return res;
}
int get_int() {
    int res = 0, ch;
    while (!((ch = getchar()) >= '0' && ch <= '9')) {
        if (ch == EOF)
            return -1;
    }
    res = ch - '0';
    while ((ch = getchar()) >= '0' && ch <= '9')
        res = res * 10 + (ch - '0');
    return res;
}

int main() {
#ifndef ONLINE_JUDGE
    freopen("data.in", "r", stdin);
    freopen("data.out", "w", stdout);
#endif
    init_prime_table(46500);
    int N = get_int();
    while(N > 0) {
        printf("%lld\n", work(N));
        N = get_int();
    }
    return 0;
}
posted @ 2012-09-27 21:25  moonbay  阅读(216)  评论(0编辑  收藏  举报