Cod sursa(job #1364243)

Utilizator mirceadinoMircea Popoveniuc mirceadino Data 27 februarie 2015 16:08:14
Problema Suma si numarul divizorilor Scor 100
Compilator cpp Status done
Runda Arhiva educationala Marime 1.99 kb
#include<cstdio>
#include<string>
#include<bitset>

using namespace std;

#ifdef HOME
const string inputFile = "input.txt";
const string outputFile = "output.txt";
#else
const string problemName = "ssnd";
const string inputFile = problemName + ".in";
const string outputFile = problemName + ".out";
#endif

typedef long long int lld;
typedef pair<lld, int> PLI;
const int MMAX = 100000 + 5;
const int MOD = 9973;

int T, M, top;
lld N;
int P[MMAX];
PLI D[MMAX];
bitset<500005> viz;

void ciur() {
    int i, j, k;

    P[++top] = 2;

    for(i = 1, j = 3; j * j <= 1000000; i++, j += 2)
        if(!viz[i]) {
            P[++top] = j;
            for(k = j * j / 2; 2 * k + 1 <= 1000000; k += j)
                viz[k] = 1;
        }

    for(; j <= 1000000; i++, j += 2)
        if(!viz[i])
            P[++top] = j;
}

void descompune(lld x) {
    int i, j;

    M = 0;

    for(i = 1; i <= top && P[i] * 1LL * P[i] <= x; i++) {
        j = 0;

        while(x % P[i] == 0) {
            x /= P[i];
            j++;
        }

        if(j)
            D[++M] = make_pair(P[i], j);
    }

    if(x > 1)
        D[++M] = make_pair(x, 1);
}

int expLog(lld B, int E) {
    if(E == 0) return 1;
    if(E == 1) return B % MOD;
    int t = expLog(B, E / 2);
    return ((t * t) % MOD * expLog(B, E % 2)) % MOD;
}

int invMod(lld B) {
    return expLog(B, MOD - 2);
}

int nr_div() {
    int i, ans = 1;

    for(i = 1; i <= M; i++)
        ans = (ans * (D[i].second + 1)) % MOD;

    return ans;
}

int sum_div() {
    int i, ans = 1, a, b;

    for(i = 1; i <= M; i++) {
        a = expLog(D[i].first, D[i].second + 1);
        a = (a + MOD - 1) % MOD;
        b = invMod(D[i].first - 1);
        ans = (ans * 1LL * a * b) % MOD;
    }

    return ans;
}

int main() {
    freopen(inputFile.c_str(), "r", stdin);
    freopen(outputFile.c_str(), "w", stdout);

    scanf("%d", &T);

    ciur();

    while(T--) {
        scanf("%lld", &N);

        descompune(N);

        printf("%d %d\n", nr_div(), sum_div());
    }

    return 0;
}