Cod sursa(job #478747)

Utilizator razvi9Jurca Razvan razvi9 Data 20 august 2010 11:17:27
Problema Suma si numarul divizorilor Scor 40
Compilator cpp Status done
Runda Arhiva educationala Marime 1.58 kb
#include <iostream>
#include <vector>
using namespace std;

vector<int> prime;

void ciur()
{
	prime.clear();

	const int max = 1000000;
	char a[max + 1];
	memset(a, 0, max + 1);

	for(int i = 2; i <= max; ++ i)
		if(!a[i])
		{
			prime.push_back(i);
			for(int j = i + i; j <= max; j += i)
				a[j] = 1;
		}
}

void solve(int);

int main()
{
	ciur();
	freopen("ssnd.in", "r", stdin);
	freopen("ssnd.out", "w", stdout);
	long long t, n;

	cin >> t;
	while(t --)
	{
		cin >> n;
		solve(n);
	}

	return 0;
}

const int mod = 9973;

void gcd(int a, int b, int &x, int &y)
{
	if(!b)
		x=1 , y=0;
	else
	{
		gcd(b,a%b,x,y);
		int aux = x;
		x = y;
		y = aux - y*(a/b);
	}
}

int inv(int a)
{
	int x, y;
	gcd(a, mod, x, y);

	x %= mod;
	if(x < 0)
		x += mod;

	return x;
}

int pow(int a, int b)
{
	if (b == 0)
		return 1;

	int c = pow(a, b >> 1);
	c = (c * c) % mod;
	if (b & 1) c = (c * a) % mod;

	return c;
}

void solve(int n)
{
	if (n == 1)
	{
		cout << 1 << " " << 1 << endl;
		return;
	}
	vector<pair<int, int> > fact;

	for(int i=0; i<prime.size() && n != 1; ++i)
	{
		int m = 0;
		while (n % prime[i] == 0)
			++ m, n /= prime[i];
		if (m)
			fact.push_back(make_pair(prime[i], m));
	}

	if (n != 1)
		fact.push_back(make_pair(n, 1));

	long long count = 1, sum = 1;
	for(int i=0; i<fact.size(); ++i)
	{
		count *= fact[i].second + 1;
		sum = (sum * (pow(fact[i].first, fact[i].second + 1) - 1) * inv(fact[i].first - 1)) % mod;
	}

	if(sum < 0)
		sum += mod;

	cout << count << " " << sum << endl;
}