CF839D Winter is here
题目分析
设\(g_i\)为序列\(gcd\)为\(i\)的个数
可以列出一个初始值\(g_i=2^{num_i}-1,num_i\)为因数有\(i\)的个数
但这样明显会算重复,对于\(\forall j,j\mid i\) ,都会有重复的
\(g_i=2^{num_i}-1-\sum\limits_{j\mid i}g_j\)
\(但对于长度,我们重新定义g_i为序列gcd为i的数的个数\)
\(g_i=\sum\limits_{i=0}^{num_i}i\times\binom{num_i}{i}-\sum\limits_{j\mid i}g_j\)
\(g_i=\sum\limits_{i=0}^{num_i}num_i\times\binom{num_i-1}{i-1}-\sum\limits_{j\mid i}g_j\)
\(g_i=num_i\times\sum\limits_{i=0}^{num_i}\binom{num_i-1}{i-1}-\sum\limits_{j\mid i}g_j\)
\(g_i=num_i\times\sum\limits_{i=1}^{num_i}\binom{num_i-1}{i-1}-\sum\limits_{j\mid i}g_j\)
\(g_i=num_i\times\sum\limits_{i=0}^{num_i-1}\binom{num_i-1}{i}-\sum\limits_{j\mid i}g_j\)
\(g_i=num_i\times2^{num_i-1}-\sum\limits_{j\mid i}g_j\)
\(最后计数即可\)
#include <bits/stdc++.h>
using namespace std;
const int MOD = 1e9+7;
long long x;
long long num[1000005];
int cnt;
long long Pow(int a, int b, int p) {
long long ans = 1;
long long base = a;
base %= p;
while (b) {
if (b & 1) {
ans *= base;
ans %= p;
}
base *= base;
base %= p;
b >>= 1;
}
return ans;
}
int n,m;
long long g[1000005];
long long ans=0;
signed main() {
scanf("%d",&n);
for(int i=1;i<=n;i++)
{
scanf("%lld",&x);
for(int j=1;j*j<=x;j++)
{
if(x%j==0)
{
num[j]++;
if(j!=(x/j))
{
num[x/j]++;
}
}
}
}
for(int i=1000000;i>=2;i--)
{
if(!num[i])
{
continue;
}
g[i]=(num[i]*Pow(2,num[i]-1,MOD)%MOD)%MOD;
for(int j=2*i;j<=1000000;j+=i)
{
g[i]=(g[i]-g[j]+MOD)%MOD;
}
ans=(ans+(g[i]*i%MOD))%MOD;
}
printf("%lld",ans);
}