2693: jzptab - BZOJ
Description
Input
一个正整数T表示数据组数
接下来T行 每行两个正整数 表示N、M
Output
T行 每行一个整数 表示第i组数据的结果
Sample Input
1
4 5
Sample Output
122
HINT
T <= 10000
N, M<=10000000
题解君:http://hi.baidu.com/mikeni2006/item/b4f78a4520de9bab61d7b985
看了一上午才看懂,最后终于在lazycal的帮助下想出来了
我们需要先预处理出那个奇怪的前缀和就是
d Σ d* Σ d'*μ(d') i=1 d'|d
然后因为trunc(n/i)和trunc(m/i)都只有根号级别个值,也就是只要枚举这些值就行了
为了跑得快,类型用的longint,然后写了很多int64函数
1 const 2 maxn=10000010; 3 h=100000009; 4 var 5 flag:array[0..maxn]of boolean; 6 f,s:array[0..maxn]of longint; 7 p:array[0..1000000]of longint; 8 t,n,m,tot:longint; 9 10 function max(x,y:longint):longint; 11 begin 12 if x>y then exit(x); 13 exit(y); 14 end; 15 16 function min(x,y:longint):longint; 17 begin 18 if x<y then exit(x); 19 exit(y); 20 end; 21 22 function get(a:longint):longint; 23 begin 24 exit(((int64(a)*a+a)>>1)mod h); 25 end; 26 27 procedure pre; 28 var 29 i,j:longint; 30 begin 31 f[1]:=1; 32 for i:=2 to 10000000 do 33 begin 34 if flag[i]=false then 35 begin 36 inc(tot); 37 p[tot]:=i; 38 f[i]:=1-i+h; 39 end; 40 for j:=1 to tot do 41 begin 42 if int64(p[j])*i>10000000 then break; 43 flag[p[j]*i]:=true; 44 if i mod p[j]=0 then 45 begin 46 f[p[j]*i]:=f[i]; 47 break; 48 end 49 else f[p[j]*i]:=int64(f[i])*f[p[j]]mod h; 50 end; 51 end; 52 for i:=1 to 10000000 do 53 s[i]:=(int64(s[i-1])+int64(f[i])*i)mod h; 54 end; 55 56 procedure main; 57 var 58 i,j,t,li,ri,lj,rj,l,r,ans:longint; 59 begin 60 read(n,m); 61 if n>m then 62 begin 63 t:=n;n:=m;m:=t; 64 end; 65 ans:=0; 66 i:=1; 67 while sqr(i)<=n do 68 begin 69 ans:=(int64(ans)+((int64(f[i])*i mod h)*get(trunc(n/i))mod h)*get(trunc(m/i)))mod h; 70 inc(i); 71 end; 72 j:=trunc(m/i); 73 i:=trunc(n/i); 74 while (i>0) and (j>0) do 75 begin 76 ri:=trunc(n/i); 77 li:=trunc(n/(i+1))+1; 78 lj:=trunc(m/(j+1))+1; 79 rj:=trunc(m/j); 80 l:=max(li,lj); 81 r:=min(ri,rj); 82 if l<=r then ans:=(int64(ans)+(int64(s[r]-s[l-1]+h)*get(i)mod h)*get(j))mod h; 83 if ri<=rj then dec(i) 84 else dec(j); 85 end; 86 writeln(ans); 87 end; 88 89 begin 90 pre; 91 read(t); 92 while t>0 do 93 begin 94 dec(t); 95 main; 96 end; 97 end.