Pagini recente » Cod sursa (job #969481) | Cod sursa (job #1438784) | Cod sursa (job #2556348) | Cod sursa (job #2107868) | Cod sursa (job #1745582)
#include <iostream>
#include <fstream>
using namespace std;
//const long long int PMAX = 100000000000000LL;
//const long long int NMAX = 12000000000LL;
long long int N, P; //Datele de intrare
long long int R; //Rezultatul problemei
long long int divp[20];
int nrd; //divizorii primi ai lui N
int nt;
ifstream f("frac.in");
ofstream g("frac.out");
void divizorip(long long int x)
{
nrd = 0;
if(x % 2 == 0)
{
divp[++nrd] = 2;
do
{
x /= 2;
}
while(x % 2 == 0);
}
for(long long int i = 3; i * i <= x; i += 2)
if(x % i == 0)
{
divp[++nrd] = i;
do
{
x /= i;
}
while(x % i == 0);
}
if(x > 1) divp[++nrd] = x;
}
long long int calcul(long long int x)
{
long long int rez = x;
//int nt = 1 << nrd; //il declaram global si facem calculul in main()
for(int i = 1; i < nt; i++)
{
long long int prod = 1;
for(int j = 0, p2; (p2 = 1 << j) <= i; j++)
{
if(i & p2)
prod *= -divp[j + 1];
}
rez += x / prod;
}
return rez;
}
int main()
{
long long N, P;
f >> N >> P;
divizorip(N);
nt = 1 << nrd;
long long int p = 1;
long long int u = 1LL << 61; //Se garanteaza ca rezultatul nu depaseste 2^61
while(p <= u)
{
long long int m = (p + u) / 2;
if(calcul(m) < P)
p = m + 1;
else
{
R = m;
u = m - 1;
}
}
g << R << endl;
f.close();
g.close();
return 0;
}