Cod sursa(job #99752)

Utilizator nicolaetitus12Nicolae Titus nicolaetitus12 Data 11 noiembrie 2007 16:03:28
Problema Fractii Scor 100
Compilator cpp Status done
Runda Arhiva de probleme Marime 1.19 kb
#include <fstream.h>
#include <math.h>
#define L 100
void aduna(long numar[],long a)
{long numar2[L];
 memset(numar2,0,L);
 long i=1,c=0;

 while(a) {numar2[i++]=a%10;a/=10;}
 numar2[0]=i-1;

 for (i=1;i<=numar2[0]||i<=numar[0]||c;i++,c/=10)
 {numar[i]=(c+=numar[i]+numar2[i])%10;}
 numar[0]=i-1;
}

void cprim(long prim[])
{long i,j,flag,varf=1;
 
 for (i=2;i<=2000;i++,flag=1)
 {for (j=2;j<=sqrt(i);j++)
  {if(i%j==0){flag=0;break;}
  }
  if(flag){prim[varf++]=i;}
 }
 prim[0]=varf--;
}

long totient(long n,long prim[])
{long m=n;
 for (long i=1;sqrt(n)>=prim[i];i++)
 {if(n%prim[i]==0)
  {m=(m/prim[i])*(prim[i]-1);
   do
   {n/=prim[i];
   }
   while(n%prim[i]==0);
  }
 }
 if(n>1){m=m/n*(n-1);}
 return m;
}

int main ()
{long prim[500],in,i;
 long temp=1;
 memset (prim,0,sizeof(prim));
 cprim(prim);
 long numar[L];
 memset(numar,0,L);
 ifstream fin("fractii.in");
 fin>>in;fin.close();
 for (i=2;i<=in;i++)
 {temp+=(long)(2L*(long)totient(i,prim));
  if(temp>2000000000)
  {aduna(numar,temp);temp=0;}
 }
 if(temp)
 {aduna(numar,temp);}
 ofstream f("fractii.out");
 for (i=numar[0];i>=1;i--)
 {f<<(char)(numar[i]+48);}
 f.close();
 return 0;
}