Cod sursa(job #2243241)

Utilizator paul_danutDandelion paul_danut Data 20 septembrie 2018 10:18:59
Problema Suma si numarul divizorilor Scor 70
Compilator cpp Status done
Runda Arhiva educationala Marime 2.26 kb
#include <fstream>
#include <math.h>
#include <iostream>

std::ifstream f("ssnd.in");
std::ofstream g("ssnd.out");

using namespace std;

constexpr int MAXN = 1000001;


//(a - b) mod p = ((a mod p - b mod p) + p) mod p
//(a / b) mod p = ((a mod p) * (b^(-1) mod p)) mod p
//Where b^(-1) mod p is the modular inverse of b mod p. For p = prime, b^(-1) mod p = b^(p - 2) mod p

void findPrimes(int primes[], int &K)
{
    bool filter[MAXN];

    for(int i=0; i<MAXN; ++i)
    {
        filter[i] = true;
    }

    K = 0;
    for(int i=2; i<MAXN; ++i)
    {
        if(filter[i])
        {
            primes[K] = i;
            ++K;

            for(int j=i+i; j<MAXN; j+=i)
            {
                filter[j] = false;
            }
        }
    }
}

int power(int x, int p, int MOD) {
    int rez = 1;
    x %= MOD;

    for(; p; p >>= 1) {
        if(p & 1) {
            rez *= x;
            rez %= MOD;
        }

        x *= x;
        x %= MOD;
    }

    return rez;
}

/*
int power(int n, int p, int mod)
{
    int r = 1;

    while( p != 1 )
    {
        if( p % 2 ==1 )
        r = (n*r) % mod;
        n = (n*n) % mod;
        p = p / 2;
    }

    return ( n * r ) % mod;
}*/

void computeValues(int &nr, int &sum, int nr_d, int prime)
{
    int mi = power(prime-1, 9971, 9973);                 ///For p = prime, b^(-1) mod p = b^(p - 2) mod p
    int prime_pow = power(prime, nr_d + 1, 9973) - 1;

    sum = (1LL * sum * prime_pow * mi) % 9973;
    nr *= nr_d + 1;
}

int primes[100000];

int main()
{
    int t=0;

    long long x=0;
    int sum = 0;
    int nr = 0;
    int K;

    findPrimes(primes, K);

    f>>t;
    while(t > 0)
    {
        f >> x;
        sum = 1;
        nr = 1;

        for(int i = 0; i < K; ++i)
        {
            auto nr_d = 0;
            while( x % primes[i] == 0 )
            {
                ++ nr_d;
                x /= primes[i];
            }

            if(nr_d > 0)
            {
                computeValues(nr, sum, nr_d, primes[i]);
            }
        }
        if(x > 1)
        {
            ++nr;
            computeValues(nr, sum, 1, x);
        }

        g << nr << ' ' << sum <<'\n';

        --t;
    }
}