【BZOJ3309】DZY Loves Math


Time Limit: 5000 ms Memory Limit: 512 MB

  

Description

  
​   對於正整數n,定義f(n)為n所含質因子的最大冪指數。例如f(1960)=f(2^3 * 5^1 * 7^2)=3, f(10007)=1, f(1)=0。
​   給定正整數a,b,求\(\sum\limits _{i=1}^a \sum\limits_{j=1}^b f(gcd(i,j))\)
  

Input

  
  第一行一個數T,表示詢問數。
  接下來T行,每行兩個數a,b,表示一個詢問。
  

Output

  
​   對於每一個詢問,輸出一行一個非負整數作為回答。
  

Sample Input

  
​   4
​   7558588 9653114
​   6514903 4451211
​   7425644 1189442
  ​ 6335198 4957
  

Sample Output

  
​   35793453939901
​   14225956593420
​   4332838845846
  ​ 15400094813
  

HINT

  
【數據規模】
  T<=10000
​  1<=a,b<=10^7
  
  
  

Solution

  
  這里用\(n\)\(m\)代表題目中的\(a\)\(b\)。-_-

\[\begin{aligned} ans&=\sum_{i=1}^n\sum_{j=1}^mf(gcd(i,j))\\ &=\sum_{x=1}^{min(n,m)}f(x)*sum(x) &sum(x)為x=gcd(i,j)的(i,j)對數,滿足i和j在n和m范圍內\\ &=\sum_{x=1}^{min(n,m)}f(x)\sum_{x|d}\mu(\frac dx)\lfloor\frac nd\rfloor\lfloor\frac md\rfloor\\ &=\sum_{x=1}^{min(n,m)}f(x)\sum_{k=1}^{\lfloor min(n,m)/x\rfloor}\mu(k)\lfloor\frac n{kx}\rfloor\lfloor\frac m{kx}\rfloor\\ &=\sum_{T=1}^{min(n,m)}\lfloor\frac nT\rfloor\lfloor\frac mT\rfloor\sum_{d|T}f(d)\mu(\frac Td)\\ &=\sum_{T=1}^{min(n,m)}\lfloor\frac nT\rfloor\lfloor\frac mT\rfloor g(T) &令g(x)=\sum\limits_{d|x}f(d)\mu(\frac xd) \end{aligned} \]

  
​ 現在關鍵是求解\(g\)函數,完事后求\(g\)的前綴和,一樣根號分段求\(ans\).
  
​ (1)當\(x\)為質數時,\(g(x)=f(1)\mu(x)+f(x)\mu(1)=0+1=1\)
  
  
  
  ​ (2)當篩到\(x=p*i\)時,分解質因數\(x=p_1^{q_1}p_2^{q_2}...p_k^{q_k}\)\(\frac xd=p_1^{a_1}p_2^{a_2}...p_k^{a_k}\),顯然\(或a_i=0或1\),才能對\(g(x)\)有貢獻,不然\(\mu({\frac xd})=0\). 現在只考慮滿足\(或a_i=0或1\)的因數\(d\).

\[\begin{aligned} g(x)&=\sum_{d|x}f(d)\mu(\frac xd)\\ &=f(x)\sum_{d|x且f(d)=f(x)} \mu(\frac xd)+(f(x)-1)\sum_{d|x且f(d)\ne f(x)}\mu(\frac xd)\\ &=-\sum_{d|x且f(d)\ne f(x)}\mu(\frac xd) \end{aligned} \]

  ​ 要滿足\(f(d)\ne f(x)\),所有\(q_i=f(x)\)\(p_i\)的指數在\(d\)中都要變成\(q_i-1\).
  
  1° 如果所有\(q_i=f(x)\),那么\(a_i\)全部取1,則\(g(x)=-\mu(p_1p_2...p_k)=-(-1)^k=(-1)^{k+1}\),這里有個特殊情況,如果\(i\)\(p\)的完全平方數,即\(i=p^{a_i}\),(這里的\(a\)是最后提到的那個\(a\)數組),那么\(x=p^{a_i+1}\),則\(g(x)=-\mu(p)=1\)
  
  2° 否則若存在\(q_i\ne f(x)\)\(g(x)=0\).
  
​   記\(A=\{i|q_i=f(x)\},B=\{i|q_i\ne f(x)\}\).
  
​   對於\(A\)中的\(i\)\(a_i\)必須取1,而\(B\)中的\(a_i\)取0或1都可以,那么

\[\begin{aligned} g(x)&=-\sum\mu((\prod_{i\in A}p_i)*(\prod_{j\in B}(p_j或1))\\ &=-\mu(\prod_{i\in A}p_i)\sum\mu(\prod_{j\in B}(p_j或1))\\ &=-(-1)^{|A|}*0&\ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \prod_{i\in B}(p_j或1)有奇數個質數和偶數個質數的情況次數一樣,正負抵消\\ &=0 &大快人心 \end{aligned} \]

​  
  
​   線性篩時,維護一個\(a_i\)表示\(i\)的最小質因子\(p_{min}\)的指數,\(b_i\)表示\(p_{min}^{a_i}\).
  
​   由於每次循環的\(p\)都是\(x\)的最小質因子,故每次更新時比較\(a_i\)\(a_x\)是否相同,如果相同就更新,如果不相同直接等於0,這樣就可以保證每一個數\(x\)如果存在質因子指數不同的情況,\(g(x)\)立即等於0. 詳情見代碼.
  
  
  

#include <cstdio>
using namespace std;
typedef long long ll;
const int N=1e7+1;
int vis[N],lis[N],cnt;
ll g[N],a[N],b[N];
inline void swap(int &x,int &y){int t=x;x=y;y=t;}
inline int min(int x,int y){return x<y?x:y;}
void init(){
	for(int i=2;i<N;i++){
		if(!vis[i]){
			lis[++cnt]=i;
			a[i]=1; b[i]=i;
			g[i]=1;
		}
		for(int j=1;j<=cnt&&i*lis[j]<N;j++){
			int x=i*lis[j],p=lis[j];
			vis[x]=1;
			if(i%p==0){
              	//d是i去除p后的數,i=d*p^ai, x=d*p^(ai+1) 故ax=ai+1,bx相應乘上p
				a[x]=a[i]+1;	
				b[x]=b[i]*p;
				int d=i/b[i];
				if(d==1) g[x]=1; //特殊情況(邊界情況)i是p的冪 
				else g[x]=(a[x]==a[d])?-g[d]:0;	 //若x滿足所有指數相同,g(x)=g(d)乘上-1,否則為0
				break;
			}
			a[x]=1; b[x]=p;
			g[x]=a[i]==1?-g[i]:0; //原理同上
		}
	}
	for(int i=2;i<N;i++) g[i]+=g[i-1];
}
int main(){
	freopen("input.in","r",stdin);
	init();
	int T,a,b;
	ll ans;
	scanf("%d",&T);
	while(T--){
		scanf("%d%d",&a,&b);
		if(a>b) swap(a,b);
		ans=0;
		for(int i=1,j;i<=a;i=j+1){
			j=min(a/(a/i),b/(b/i));
			ans+=1LL*(a/i)*(b/i)*(g[j]-g[i-1]);
		}
		printf("%lld\n",ans);
	}
	return 0;
}


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM