BZOJ 1114 Number theory(莫比乌斯反演+预处理)

题目链接:http://acm.hust.edu.cn/vjudge/problem/viewProblem.action?id=71738

题意:给你一个整数序列a1, a2, a3, ... , an。求gcd(ai, aj) = 1 且 i < j的对数。

思路:利用莫比乌斯反演很快就能得到公式,但是求解时我们要知道序列中1, 2, 3, ... , max(a1, a2, ... , an)的倍数各是多少。我们用num[i]=k,来表示序列中有k个数是i的倍数,那么这部分对结果的影响是mu[i]*(k - 1) * k / 2。最后的结果就是sigma(mu[i]*(k - 1) * k / 2)。

code:

 1 #include <cstdio>
 2 #include <cstring>
 3 #include <algorithm>
 4 using namespace std;
 5 typedef long long LL;
 6 const int MAXN = 250000;
 7 int num[MAXN];        // num[i]表示 满足(i|ak)的个数
 8 int tmp[MAXN];        // 标记哪些数有
 9 bool check[MAXN];
10 int primes[MAXN];
11 int mu[MAXN];
12
13 void moblus()
14 {
15     memset(check, false, sizeof(check));
16     mu[1] = 1;
17     int cnt = 0;
18     for (int i = 2; i < MAXN; ++i) {
19         if (!check[i]) {
20             primes[cnt++] = i;
21             mu[i] = -1;
22         }
23         for (int j = 0; j < cnt; ++j) {
24             if (i * primes[j] > MAXN) break;
25             check[i * primes[j]] = true;
26             if (i % primes[j] == 0) {
27                 mu[i * primes[j]] = 0;
28                 break;
29             } else {
30                 mu[i * primes[j]] = -mu[i];
31             }
32         }
33     }
34 }
35
36 int main()
37 {
38     moblus();
39     int n;
40     while (scanf("%d", &n) != EOF) {
41         memset(num, 0, sizeof(num));
42         memset(tmp, 0, sizeof(tmp));
43         int tmax = 0;
44         for (int i = 0; i < n; ++i) {
45             int x;
46             scanf("%d", &x);
47             ++tmp[x];
48             tmax = max(tmax, x);
49         }
50         for (int i = 1; i <= tmax; ++i) {
51             for (int j = i; j <= tmax; j += i) {
52                 num[i] += tmp[j];
53             }
54         }
55         LL ans = 0;
56         for (int i = 1; i <= tmax; ++i) {
57             ans += (LL)mu[i] * num[i] * (num[i] - 1) / 2;
58         }
59         printf("%lld\n", ans);
60     }
61     return 0;
62 }
时间: 2024-10-13 12:29:20

BZOJ 1114 Number theory(莫比乌斯反演+预处理)的相关文章

Acdream 1114 Number theory 莫比乌斯反演

http://acdream.info/problem?pid=1114 题目大意,给你一个序列a,求出这个序列中互质数的有多少对.其中所有的整数的都小于等于222222. f(d) 为 gcd 恰好为 d 的数的对数, F(d) 为 gcd 为 d 的倍数的对数, μ(d) 表示莫比乌斯函数 F(d) = ∑ f(n) 其中( n % d == 0 ) 莫比乌斯反演一下就可以得到, f(d) = ∑ μ(n / d) * F(n) 其中( n % d == 0) 所以我们最后所要的答案就是 f

Acdream 1117 Number theory(莫比乌斯反演)

题目链接: http://acdream.info/problem?pid=1114 题意: 给定一个序列,求序列中互质的数的对数. 分析: 我们设f(d) 表示gcd恰好为d的数的个数,F(d)表示gcd为d的倍数的个数 因此,F(d) = sigma (f(n))  (n%d==0) f(n)= sigma( mu[d]*F[n/d] ) (n%d==0); 因此我们先统计出每个数出现的频数num; 然后用cnt[i]表示i的倍数的个数. F(i) = C(cnt[i],2); 我们最终要求

bzoj 2820 / SPOJ PGCD 莫比乌斯反演

那啥bzoj2818也是一样的,突然想起来好像拿来当周赛的练习题过,用欧拉函数写掉的. 求$(i,j)=prime$对数 \begin{eqnarray*}\sum_{i=1}^{n}\sum_{j=1}^{m}[(i,j)=p]&=&\sum_{p=2}^{min(n,m)}\sum_{i=1}^{\lfloor\frac{n}{p}\rfloor}\sum_{j=1}^{\lfloor\frac{m}{p}\rfloor}[i⊥j]\newline&=&\sum_{p=

bzoj 1101 [POI2007]Zap - 莫比乌斯反演

Description FGD正在破解一段密码,他需要回答很多类似的问题:对于给定的整数a,b和d,有多少正整数对x,y,满足x<=a ,y<=b,并且gcd(x,y)=d.作为FGD的同学,FGD希望得到你的帮助. Input 第一行包含一个正整数n,表示一共有n组询问.(1<=n<= 50000)接下来n行,每行表示一个询问,每行三个 正整数,分别为a,b,d.(1<=d<=a,b<=50000) Output 对于每组询问,输出到输出文件zap.out一个正

BZOJ 2440 完全平方数(莫比乌斯反演+二分查找)

题目链接:http://acm.hust.edu.cn/vjudge/problem/viewProblem.action?id=23362 题意:定义含有平方数因子的数为完全平方数(平方数因子不包含1).求第k个非完全平方数. 思路:我们先求出[1, n]的非完全平方数的个数,然后利用二分来查找正好等于k时的n(注意这样的n可能不止一个,求最左边的).关键是,怎么求出前者,我们可以利用容斥原理,用n - [1, n]内完全平方数的个数,求[1, n]内完全平方数的个数,用容斥发现前面的系数就是

bzoj 3529 [Sdoi2014]数表 (莫比乌斯反演+树状数组+离线)

题目大意:有一张$n*m$的数表,第$i$行第$j$列的数是同时能整除$i,j$的所有数之和,求数表内所有不大于A的数之和 先是看错题了...接着看对题了发现不会做了...刚了大半个下午无果 看了Po姐的题解(Orzzz)才搞懂这道题,搞清楚了莫比乌斯反演的两种经典的卷积形式的不同之处 令$\sigma(i)$表示i的约数个数和 如果去掉A这个限制,则题目是让我们求$\sum_{i=1}^{n}\sum_{j=1}^{m}\sigma(gcd(i,j))$ 考虑如何正确转化式子,让我们能够把不大

BZOJ 2693 jzptab 【莫比乌斯反演】

Description Hint T <= 10000 N, M<=10000000 Solution 和 BZOJ 2154 数字表格 几乎一样,只不过询问变成多组,之前的复杂度又过不了了 依旧写开答案 又有两个枚举量 我们尝试改变求和指标+前缀和继续减掉一个枚举量 于是就有了 对于这个东西我们定义它为 h ( D ) 使可以进行前缀和预处理的 考虑枚举 i 和 i 的倍数 然而这样的处理显然也是接受不了的 似乎只有O(n)的复杂度才可能接受 能不能把 h 放到线性筛之中处理出来呢 对于一个

bzoj 2301 Problem b - 莫比乌斯反演

Description 对于给出的n个询问,每次求有多少个数对(x,y),满足a≤x≤b,c≤y≤d,且gcd(x,y) = k,gcd(x,y)函数为x和y的最大公约数. Input 第一行一个整数n,接下来n行每行五个整数,分别表示a.b.c.d.k Output 共n行,每行一个整数表示满足要求的数对(x,y)的个数 Sample Input 22 5 1 5 11 5 1 5 2 Sample Output 143 HINT 100%的数据满足:1≤n≤50000,1≤a≤b≤50000

BZOJ 3529: [Sdoi2014]数表 [莫比乌斯反演 树状数组]

3529: [Sdoi2014]数表 Time Limit: 10 Sec  Memory Limit: 512 MBSubmit: 1399  Solved: 694[Submit][Status][Discuss] Description 有一张N×m的数表,其第i行第j列(1 < =i < =礼,1 < =j < =m)的数值为能同时整除i和j的所有自然数之和.给定a,计算数表中不大于a的数之和. Input 输入包含多组数据.    输入的第一行一个整数Q表示测试点内的数据