# HDU6434 Count【欧拉函数 线性筛】

 HDU6434 I. Count

T次询问，每次询问$\sum_{i=1}^{n}\sum_{j=1}^{n-1}[gcd(i-j,i+j)=1]$

$T\le 1e5, n \le 2e7$

对原式进行转换，枚举$i-j$$i-j$$j$ ，那么可以变换为$\sum_{i=1}^{n}\sum_{j=1}^{i-1}[gcd(j,2i-j)=1]$

$\Rightarrow \sum_{i=1}^{n}\sum_{j=1}^{i-1}[gcd(j,2i)=1]$

//#pragma GCC optimize("O3")
#include<bits/stdc++.h>
using namespace std;
function<void(void)> ____ = [](){ios_base::sync_with_stdio(false); cin.tie(0); cout.tie(0);};
const int MAXN = 2e7+7;
using LL = int_fast64_t;
int phi[MAXN];
LL sum[MAXN];
void calphi(){
for(int i = 1; i < MAXN; i++) phi[i] = i;
vector<int> prime;
for(int i = 2; i < MAXN; i++){
if(phi[i]==i){
prime.emplace_back(i);
phi[i] = i - 1;
}
for(int j = 0; j < (int)prime.size(); j++){
if(i*prime[j]>=MAXN) break;
phi[prime[j]*i] = phi[prime[j]] * phi[i];
if(i%prime[j]==0){
phi[i*prime[j]] = phi[i] * prime[j];
break;
}
}
}
for(int i = 1; i < MAXN; i++){
if(i&1) sum[i] = sum[i-1] + phi[i] / 2;
else sum[i] = sum[i-1] + phi[i];
}
}
int main(){
calphi();
____();
int T;
for(cin >> T; T; T--){
int n; cin >> n;
cout << sum[n] << endl;
}
return 0;
}

posted @ 2020-03-25 22:26  _kiko  阅读(...)  评论(...编辑  收藏