Cod sursa(job #1184597)

Utilizator crucerucalinCalin-Cristian Cruceru crucerucalin Data 13 mai 2014 13:44:21
Problema Suma si numarul divizorilor Scor 70
Compilator cpp Status done
Runda Arhiva educationala Marime 1.2 kb
#include <cstdio>

const int MOD = 9973;
const int NMAX = 1000005;
const int NMAX_DIV = 130000;

unsigned char V[NMAX/2/8 + 1];
int K, PRIM[NMAX_DIV];

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

	for (i = 1; ((i * i) << 1) + (i << 1) <= N; ++i) {
		if ((V[i >> 3] & (1 << (i & 7))) == 0) {
			for (j = ((i * i) << 1) + (i << 1); (j << 1) + 1 <= N;
			     j += (i << 1) + 1) {
				V[j >> 3] |= (1 << (j & 7));
			}
		}
	}

	PRIM[K] = 2;
	for (i = 1; (i << 1) + 1 <= N; ++i)
		if ((V[i >> 3] & (1 << (i & 7))) == 0)
			PRIM[++K] = (i << 1) + 1;
}

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

	int T;
	long long N;

	ciur(NMAX);

	scanf("%d", &T);
	for (; T; --T) {
		scanf("%lld",&N);
		
		int nr_div = 1, sum = 1;

		for (int i = 0; i <= K; ++i) {
			if (1LL * PRIM[i] * PRIM[i] > N)
				break;
			if (N % PRIM[i])
				continue;

			unsigned long long p = PRIM[i];
			int count = 0;
			while (N % PRIM[i] == 0) {
				N /= PRIM[i];
				++count;
				p *= (unsigned long long)PRIM[i] % MOD;
			}

			nr_div *= (count + 1);
			sum = ((sum * (p - 1))/(PRIM[i] - 1)) % MOD;
		}
		
		if (N > 1) {
			nr_div *= 2;
			sum = (1LL * sum * (N+1)) % MOD;
		}

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

	return 0;
}