1. 程式人生 > 其它 >luogu P2260 [清華集訓2012]模積和 |數論分塊

luogu P2260 [清華集訓2012]模積和 |數論分塊

題目描述

\(\sum_{i=1}^{n} \sum_{j=1}^{m} (n \bmod i) \times (m \bmod j), i \neq j\) mod 19940417 的值

輸入格式

輸入只有一行兩個整數 \(n\)\(m\)

#include<cstdio>
#include<cstring>
#include<iostream>
using namespace std;
#define int long long
const int mod=19940417;
inline int ksm(int x,int y){
	int ans=1;
	while(y){
		if(y&1)ans=ans*x%mod;
		x=x*x%mod; y>>=1;
	}
	return ans;
}
inline int sum1(int p,int q){
	return (((q+p)*(q-p+1))>>1 )%mod;
}
int inv=ksm(6,17091779);
inline int sum2(int x){
	return (x*(x+1))%mod*(2*x+1)%mod*inv%mod;
}
int cal(int n){
	int ans=0;
	for(int l=1,r=0;l<=n;l=r+1){
		r=n/(n/l);
		ans=(ans+ n*(r-l+1)%mod -sum1(l,r)*(n/l)%mod +mod )%mod;
	}
	return ans;
}

signed main(){
	int n,m;
	cin>>n>>m;
	int ans=cal(n)*cal(m)%mod;
	if(n>m)swap(n,m);

	for(int l=1,r=0;l<=n;l=r+1){
		r=min(n/(n/l),m/(m/l));
		int op1=(n/l),op2=(m/l);
		ans=(ans- (n*m%mod*(r-l+1))%mod+mod)%mod;
		ans=(ans- op1*op2%mod*(sum2(r)-sum2(l-1)+mod)%mod+mod)%mod;
		ans=(ans+ (op1*m%mod+op2*n%mod)*sum1(l,r)%mod)%mod;
	}
	
	cout<<(ans%mod+mod)%mod<<endl;
}
不以物喜,不以己悲