关于欧拉函数的讲解不再赘述,直接贴代码
方法一、质因数分解法,对于一个数x,时间复杂度最坏O(n)(当n为质数时)
hdu1286
var
t,x,ans :longint;
function find(n:longint):longint;
var
p:longint;
begin
ans:=n;p:=2;
while (n>1) do
begin
if n mod p=0 then
begin
ans:=ans*(p-1) div p;
while (n mod p=0) do n:=n div p;
end;
inc(p);
end;
exit(ans);
end;
begin
read(t);
while (t>0) do
begin
dec(t);
read(x);
writeln(find(x));
end;
end.
var
x,t :longint;
ans :int64;
function find(n:longint):int64;
begin
t:=2;ans:=n;
while (n>1) do
begin
if n mod t=0 then
begin
ans:=ans*(t-1) div t;
while (n mod t=0) do n:=n div t;
end;
inc(t);
end;
exit(ans);
end;
begin
read(x);
while (x<>0) do
begin
writeln(find(x));
read(x);
end;
end.
hdu 1787
求小于n且不与n互质的数的个数=n-1-phi(n)
var
ans,x,t :int64;
function find(n:longint):int64;
var
p:longint;
begin
ans:=n;
for p:=2 to trunc(sqrt(n)) do
begin
if n mod p=0 then
begin
ans:=ans*(p-1) div p;
while (n mod p=0) do n:=n div p;
end;
end;
if n>1 then ans:=ans*(n-1) div n;
exit(ans);
end;
begin
read(x);
while (x<>0) do
begin
writeln(x-find(x)-1);
read(x);
end;
end.
三、线性快速筛欧拉函数 对于范围n 时间复杂度O(n)
就是在快速线性筛质数改了几步:
1.对于筛出来的素数,φ(P)=P-1.
在while循环内
2.若i mod prime[j]=0,那么φ(i*prime[j])=φ(i)*prime[j]
3.若i mod prime[j]≠0,那么φ(i*prime[j])=φ(i)*(prime[j]-1)
hdu2824
var
eul :array[0..3000010] of int64;
vis :array[0..3000010] of boolean;
prime :array[0..217000] of longint;
ans,t :int64;
i :longint;
a,b :longint;
procedure pre_do;
var
i,j:longint;
begin
eul[1]:=1;
for i:=2 to 3000000 do
begin
if not vis[i] then
begin
inc(t);
prime[t]:=i;
eul[i]:=i-1;
end;
for j:=1 to t do
if (prime[j]*i>3000000) then break else
begin
vis[i*prime[j]]:=true;
if (i mod prime[j]<>0) then eul[i*prime[j]]:=eul[i]*eul[prime[j]] else
begin
eul[i*prime[j]]:=eul[i]*prime[j];break;
end;
end;
end;
end;
begin
pre_do;
while not eof do
begin
readln(a,b);
ans:=0;
for i:=a to b do inc(ans,eul[i]);
writeln(ans);
end;
end.
——by Eirlys