題目描述
有人問現實中爲什麼總是男生追求女生,反過來很少。實際上女生也是想主動追求男生的,但是世俗中對於主動追求男生的女生有種歧視,這樣就使得女生不大敢主動追求男生。但是面對喜歡的男生,難道就不出手麼?女生只能步步爲營,挖坑來引誘男生往裏跳。這時候問題就來了,挖掘機技術到底哪家強?
被熱血沸騰的廣告洗腦了若干天后,Matt終於下定決心,毅然登上了開往泉城的列車,決心尋找生活的希望。
來到布魯謝特學院後,Matt逐漸地瞭解了各種型號的挖掘機。在這裏我們可以認爲有大挖掘機和小挖掘機兩種。
今天Matt的任務很簡單:首先他要用大挖掘機挖出恰好N單位體積的砂土。由於小挖掘機比較笨拙,它每次挖的砂土體積是固定的。也就是說,設每次挖x單位體積砂土,那麼N需要被x整除。在挖出若干堆體積爲x的砂土後,Matt需要計算x的“難挖指數”。體積x的“難挖指數”定義如下:對於某個不超過x的體積y,如果x與y的最大公約數爲1,那我們認爲體積y是“難挖的”,x的“難挖指數”就要加上y。
由於Matt之後還需要用小挖掘機處理被大挖掘機挖出的砂土,他希望知道所有可能的x的難挖指數的和,這樣他好估算今天要幹多久,不然作爲布魯謝特的高才生,他出門要被笑話的。
輸入
第一行一個整數T,表示數據組數。
接下來T行每行一個整數表示N。
輸出
對於每個數據輸出一行一個整數表示難挖指數的和。
樣例輸入
3
2
3
4
樣例輸出
2
4
6
提示
對於30%的數據有T<=20,N<=10^4。
對於60%的數據有T<=100,N<=10^7。
對於100%的數據有1<=T<=1000,1<=N<=10^9。
通過打表發現規律。
答案=((n的所有的因數i的歐拉函數值*i)+1)/2(這裏的+1是爲了防止除不開(當然實際上一定會除不開所以加一沒毛病))
證明:若a與n互質,那麼n-a與n也互質。我們把a與n-a結成一對,那麼n以內就存在phi(n)/2對,每一對的和都爲n。
然後歐拉函數優化——歐拉篩法
然後就以飛速AC啦!
#include<cstdio>
#include<cstring>
#include<cmath>
#include<algorithm>
using namespace std;
long long sum;
int su[1000000]={0},he[1000000]={0};
int cnt=0;
void eular(int n){
if(n==1||n==2){
sum++;
return;
}
long long ans=n,a=n;
for(int i=1;i<=cnt;i++){
if(n%su[i]==0){
ans=ans/su[i]*(su[i]-1);
while(n%su[i]==0){
n/=su[i];
}
}
if(n==1)break;
}
if(n>1){
ans=ans/n*(n-1);
}
sum+=ans*a/2;
return;
}
void Euler(int n){
for(int i=2;i<=n;i++){
if(he[i]==0){
cnt++;
su[cnt]=i;
}
for(int j=1;j<=cnt&&i*su[j]<=n;j++){
he[su[j]*i]=1;
if(i%su[j]==0)break;
}
}
}
int main(){
Euler(100000);
int t;
scanf("%d",&t);
while(t--){
int n;
scanf("%d",&n);
sum=0;
for(int i=1;i*i<=n;i++){
if(n%i==0){
eular(i);
if(i!=n/i){
eular(n/i);
}
}
}
printf("%lld\n",sum);
}
return 0;
}