牛客练习赛76 F phi and phi (莫比乌斯反演)

题目链接:https://ac.nowcoder.com/acm/contest/10845/F

如图:

#include<bits/stdc++.h>
using namespace std;
typedef long long ll;

const int maxn = 1000010; 
const int M = 1000000007;

int n, m;
int ans[maxn];

int is[maxn], prime[maxn], phi[maxn];

ll read(){ ll s = 0, f = 1; char ch = getchar(); while(ch < '0' || ch > '9'){ if(ch == '-') f = -1; ch = getchar(); } while(ch >= '0' && ch <= '9'){ s = s * 10 + ch - '0'; ch = getchar(); } return s * f; }

int main(){
	n = read();
	is[1] = phi[1] = 1;
	for(int i = 2 ; i <= n ; ++i){
		if(!is[i]){
			prime[++m] = i;
			phi[i] = i - 1;
		}
		for(int j = 1 ; j <= m && i * prime[j] <= n ; ++j){
			is[i * prime[j]] = 1;
			if(i % prime[j] == 0){
				phi[i * prime[j]] = phi[i] * prime[j];
				break;
			} else {
				phi[i * prime[j]] = phi[i] * (prime[j] - 1); 
			}
		}
	}
	
	for(int i = 1 ; i <= n ; ++i){
		int sum = 0;
		for(int j = i ; j <= n ; j += i){
			sum = (sum + phi[j]) % M;
			ans[j] = (ans[j] + 1ll * sum * sum % M * phi[i] % M) % M;
			ans[j + i] = ((ans[j + i] - 1ll * sum * sum % M * phi[i] % M) % M + M) % M;
		}
	}
	
	for(int i = 1 ; i <= n ; ++i){
		ans[i] = (ans[i] + ans[i - 1]) % M;
		printf("%d\n", ans[i]);
	}
	
	return 0;
}
posted @ 2021-01-24 11:57  Tartarus_li  阅读(93)  评论(0编辑  收藏  举报