Cod sursa(job #289185)

Utilizator rupraRupra C rupra Data 26 martie 2009 15:31:03
Problema Suma divizorilor Scor 70
Compilator cpp Status done
Runda Arhiva de probleme Marime 1.42 kb
#include <algorithm>
#include <stdio.h>
#include <vector>

#define restRez 9901
#define pb push_back
#define mp make_pair
#define f first
#define s second

using namespace std;

int a, b;
vector <pair <int, int> > vctDiv;

void euclidExtins(int a, int b, int &x, int &y)
{
	if (!b)
	{
		x = 1;
		y = 0;
		
		return;
	}
	
	euclidExtins(b, a % b, x, y);
	int xp = x;
	x = y;
	y = xp - (a / b) * y;
}	

int ridLaPutere(int x, int exp)
{
	int r = 1, nr = x;
	for (; exp > 1; r %= restRez, nr %= restRez, exp /= 2)
	{
		if (exp & 1)
			r *= nr;
		nr *= nr;
	}
	
	return (r * nr) % restRez;
}		

int calc(int fact, int exp)
{
	int p, AUX, invMod;
	p = ridLaPutere(fact, exp + 1);
	
	p = (p + restRez - 1) % restRez;
	
	euclidExtins(fact - 1, restRez, invMod, AUX);
	if (invMod < 0)
		invMod += restRez;
	
	p = (p * invMod) % restRez;
	
	return p;
}

int main()
{
	freopen("sumdiv.in", "r", stdin);
	freopen("sumdiv.out", "w", stdout);
	
	scanf("%d %d", &a, &b);
	
	int x = a;
	for (int i = 2; i * i <= a; i++)
		if (x % i == 0)
		{
			int exp = 0;
			
			for (; x % i == 0; exp++, x /= i);
			
			vctDiv.pb(mp(i % restRez, exp * b));
		}
	if (x > 1)
		vctDiv.pb(mp(x % restRez, b));
	
	int sol = 1;
	for (int i = 0; i < vctDiv.size(); i++)
		sol = (sol * calc(vctDiv[i].f, vctDiv[i].s)) % restRez;
	
	printf("%d\n", sol);

	fclose(stdin);
	fclose(stdout);
	return 0;
}