Cod sursa(job #281284)

Utilizator tomescu_alinTomescu Alin tomescu_alin Data 14 martie 2009 00:06:05
Problema Fractii Scor 100
Compilator cpp Status done
Runda Arhiva de probleme Marime 1.35 kb
#include <iostream>
#include <fstream>
#include <cmath>
using namespace std;

typedef unsigned long ulong;
typedef unsigned int uint;
typedef unsigned long long ulonglong;

// n = suma (totient[i]) unde i il divide pe n...
// totient[i] = i-1 daca i este prim
// deci max(totient[i]) oricare ar fi i din N este i-1
// deci putem calcula totient[i] scazand din i-1 toti totient[d] unde d il divide pe i (inclusiv d=1 si d=8)

/* Ex:
8 = tot(1) + tot(2) + tot(4) + tot(8) => tot(8) = 8-1 - (tot(2)+tot(4))
6 = tot(1) + tot(2) + tot(3) + tot(6) => tot(6) = 6-1 - (tot(2)+tot(3))
5 = tot(1) + tot(5) => tot(5) = 5-1 (5 e prim)
4 = tot(1) + tot(2) + tot(4) => tot(4) = 4-1 - tot(2)
3 = tot(1) + tot(3) => tot(3) = 3-1 (3 e prim)
2 = tot(1) + tot(2) => tot(2) = 2-1 (2 e prim)
*/
void generateTotients (ulonglong * totient, ulong n)
{	
	for (ulong i = 2; i <= n; ++i)
		totient[i] = i-1;
		
	for (ulong i = 2; i <= n; ++i)
		for (uint j = 2 * i; j <= n; j += i)
			totient[j] -= totient[i];
}

int main()
{
	ifstream fin ("fractii.in");
	ofstream fout ("fractii.out");

	ulong n;
	fin >> n;
	
	ulonglong totient[n+1];
	generateTotients (totient, n);
	ulonglong total = 0;
	
	for (ulonglong i = 2; i <= n; i++)
	{
		total += totient [i];
	}
	total = (total * 2) + 1;
	
	fout << total;
	
	fout.close();
	fin.close();
	
	return 0;
}