码迷,mamicode.com
首页 > 其他好文 > 详细

P2260 [清华集训2012]模积和

时间:2020-07-12 22:22:29      阅读:55      评论:0      收藏:0      [点我收藏+]

标签:etc   for   sum   iostream   main   inline   name   code   print   

\(a\mod b=a-b(a/b)\)

所以

\(\sum\limits_{i=1}^n\sum\limits_{j=1}^m(n\mod i)\times(m\mod j)=\sum\limits_{i=1}^n(n\mod i)\sum\limits_{j=1}^m(m\mod j)-\sum\limits_{i=1}^n(n\mod i)(m\mod j)\)

\(f(n,x)=\sum\limits_{i=1}^ni(x/i)\)

\(\sum\limits_{i=1}^n(n\mod i)=\sum\limits_{i=1}^nn-i(n/i)=n^2-\sum\limits_{i=1}^ni(n/i)\)

so

\(\begin{aligned}原式&=(n^2-f(n,n))(m^2-f(m,m))-\sum\limits_{i=1}^n(n\mod i)(m\mod i)\\&=(n^2-f(n,n))(m^2-f(m,m))-\sum\limits_{i=1}^n(n-i(n/i))(m-i(m/i))\end{aligned}\)

推导容斥的部分

\(\begin{aligned}\sum\limits_{i=1}^n(n-i(n/i))(m-i(m/i))&=\sum\limits_{i=1}^n(n-i(n/i))m-(n-i(n/i))i(m/i)\\&=\sum\limits_{i=1}^nnm-mi(n/i)-ni(n/i)+i^2(n/i)(m/i)\\&=n^2m-m\sum\limits_{i=1}^ni(n/i)-n\sum\limits_{i=1}^ni(m/i)+\sum\limits_{i=1}^ni^2(n/i)(m/i)\\&=n^2m-mf(n,n)-nf(n,m)+\sum\limits_{i=1}^ni^2(n/i)(m/i)\end{aligned}\)

最后一个 \(\sum\limits\) 还是可以除数分块 \(O(\sqrt n)\) 求。

so 预处理 \(f(n,n),f(n,m),f(m,m)\) 和上面的东西,就做完了。

最终复杂度 \(O(\sqrt n)\)

\(Code:\)

#include <iostream>
#include <cstdio>
#include <cstring>
using namespace std;
typedef long long ll;
const ll P=19940417;
inline ll read(){
	register ll x=0,f=0,ch=getchar();
	while(‘0‘>ch||ch>‘9‘)f^=ch==‘-‘,ch=getchar();
	while(‘0‘<=ch&&ch<=‘9‘)x=(x<<1)+(x<<3)+(ch^‘0‘),ch=getchar();
	return f?-x:x;
}
inline ll sum0(ll l,ll r){
	return 1LL*(r-l+1)*(l+r)%P*9970209%P;
}
inline ll sum(ll x){
	x%=P;
	return (1LL*x*(x+1)%P*((x+x)%P+1)%P*3323403%P)%P;
}
inline ll solve(ll t,ll x){
	register ll res=0;
	for(register int l=1,r;l<=t;l=r+1){
		if(x/l==0)r=t;
		else r=min(x/(x/l),t);
		res+=1LL*sum0(l,r)*(x/l)%P;
		res%=P;
	}	
	return res%P;
}
ll a,b,c;
ll n,m,f1,f2,f3,f4,ans;
inline void solved(){
	for(register int l=1,r;l<=n;l=r+1){
		r=min(n/(n/l),m/(m/l));
		f4+=1LL*(sum(r)%P-sum(l-1)%P+P)%P*(n/l)%P*(m/l)%P;
		f4%=P;
	}
}
signed main(){
	n=read(),m=read();
	if(n>m)n^=m^=n^=m;
	f1=solve(n,n);
	f2=solve(n,m);
	f3=solve(m,m);
	solved();
	ans=1LL*(1LL*n*n%P-f1+P)%P*(1LL*m*m%P-f3+P)%P;
	ans-=1LL*(1LL*n*n%P*m%P-(1LL*m*f1%P)-(1LL*n*f2%P)+f4)%P;
	ans=(ans+P)%P;
	printf("%lld\n",ans);
	return 0;
}

P2260 [清华集训2012]模积和

标签:etc   for   sum   iostream   main   inline   name   code   print   

原文地址:https://www.cnblogs.com/jasony/p/13290117.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!