题意:求第K个和M互质的数.
分析:求一个数和多少个数互质可以用容斥原理,二分一个数验证是不是第K个即可(16MS).
(另一种用欧拉函数的算法更快.)
code:
var p,c:array[0..10000] of longint;
prime:array[0..100] of longint;
v:array[0..1000001] of boolean;
u:array[0..100] of boolean;
m,n,k,i,nx,num:longint;
l,r,mid,t:int64;
procedure make(k,num:longint);
var o:longint;
begin
if k>nx then exit;
inc(n);
p[n]:=num;
c[n]:=k;
v[num]:=true;
for o:=1 to nx do
if not u[o] then
begin
u[o]:=true;
num:=num*prime[o];
if not v[num] then make(k+1,num);
num:=num div prime[o];
u[o]:=false;
end;
end;
function calc(num:int64):int64;
var o:longint;
tmp:int64=0;
begin
for o:=1 to n do
if odd(c[o]) then tmp:=tmp-num div p[o]
else tmp:=tmp+num div p[o];
exit(tmp);
end;
begin
while not seekeof do
begin
readln(m,k);
num:=m;
nx:=0;
for i:=2 to trunc(sqrt(m)) do
if num mod i=0 then
begin
inc(nx);
prime[nx]:=i;
while num mod i=0 do num:=num div i;
end;
if num>1 then
begin
inc(nx);
prime[nx]:=num;
end;
n:=0;
fillchar(v,sizeof(v),0);
make(0,1);
l:=1; r:=1<<60;
while l<r do
begin
mid:=(l+r)>>1;
t:=calc(mid);
if t>k then r:=mid-1
else if t<k then l:=mid+1
else r:=mid;
end;
writeln(l);
end;
end.
浙公网安备 33010602011771号