浅谈算法——莫比乌斯反演
前言
莫比乌斯反演(又称懵逼钨丝繁衍),那种让人看了就懵逼的东西(其实是我太菜了)
莫比乌斯反演在知道之后对解题十分有帮助,\(O(n)\)的柿子分分钟化成\(O(\sqrt n)\)
那么,什么是莫比乌斯反演呢?
莫比乌斯反演
1.莫比乌斯反演
如果说,有\(f(n)\)和\(g(n)\)是定义在正整数集合上的两个函数,并且满足
\[f(n)=\sum\limits_{d|n} g(d)\]
那么就有
\[g(n)=\sum\limits_{d|n} f(\dfrac{n}{d})\times \mu(d)\]
这个变形也就是莫比乌斯反演
2.莫比乌斯函数(性质/证明)
对于任意整数n,满足
\[\sum\limits_{d|n} \mu(d)=\begin{cases}1&,n=1\\0&,n>1\end{cases}\]
证明:
- n=1时显然
- n>1时,设\(n=P_1^{x_1}\times P_2^{x_2}\times ...\times P_k^{x_k}\),其中\(P_i(1\leqslant i\leqslant k)\)为n的互质因子,我们设\(d=P_1^{y_1}\times P_2^{y_2}\times ...\times P_k^{y_k}\),其中\(0\leqslant y_i\leqslant x_i(1\leqslant i\leqslant k)\),当存在一个\(y_i\geqslant2\)的话,那么\(\mu(d)=0\),因此我们只要考虑\(y_i=0,1\)的情况。假设d中含有r个n的互质因子,且这些质因子的指数为1,那么\(\mu(d)=(-1)^r\),这样的d一共有\(\binom{k}{r}\)个。
那么\(\sum\limits_{d|n} \mu(d)=\sum\limits_{r=0}^k \binom{k}{r}\times (-1)^r=(1-1)^k=0\)
莫比乌斯函数\(\mu(n)\)是个积性函数,证明略。
这说明\(\mu(n)=\prod\limits_{i=1}^k \mu(P_i^{x_i})\)
由于莫比乌斯函数的这些性质,使得它可以用欧拉筛在线性时间内求出
3.莫比乌斯反演(性质/证明)
首先我们证明一下第一个柿子的正确性
\[g(n)=\sum\limits_{d|n}f(\dfrac{n}{d})\times \mu(d)=\sum\limits_{d|n}\mu(d) \sum\limits_{i|\frac{n}{d}}g(i)\Longrightarrow\sum\limits_{i|n}g(i)\sum\limits_{i\times d|n}\mu(d)=\sum\limits_{i|n}g(i)\sum\limits_{d|\frac{n}{i}}\mu(d)\]
箭头转换的时候,将\(g(i)\)提前枚举了
我们现在考虑一下\(\sum\limits_{d|\frac{n}{i}}\mu(d)\)的取值
- 当i=n时,\(\sum\limits_{d|\frac{n}{i}}\mu(d)=1,g(i)\sum\limits_{d|\frac{n}{i}}\mu(d)=g(n)\)
- 当i为小于n的约数时,\(\sum\limits_{d|\frac{n}{i}}\mu(d)=0,g(i)\sum\limits_{d|\frac{n}{i}}\mu(d)=0\)
所以\(g(n)=\sum\limits_{d|n}f(\dfrac{n}{d})\times \mu(d)\)得证
莫比乌斯函数有个性质:
当\(f(n)/g(n)\)中的任意一个为积性函数后,另一个也同样为积性函数
这个性质保证了其在之后能够进行线筛。
证明略(证明太长,我懒得写)
4.莫比乌斯函数的应用
- \(g(i)\)很难直接求,但\(\sum\limits_{d|i}g(d)\)很好求,我们就可以用莫比乌斯反演来求\(g(i)\):\[f(i)=\sum\limits_{d|i}g(d)\Rightarrow g(i)=\sum\limits_{d|i}f(\dfrac{i}{d})\times \mu(d)\]
- \(g(i)\)很难直接求,但\(\sum\limits_{d=1}^{\frac{n}{i}}g(d)\)很好求,我们就可以用莫比乌斯反演来求\(g(i)\):\[f(i)=\sum\limits_{d=1}^{\frac{n}{i}}g(d\times i)\Rightarrow g(i)=\sum\limits_{d=1}^{\frac{n}{i}}f(d\times i)\mu(d)\]
例题
[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一个正整数,表示满足条件的整数对数。
Sample Input
2
4 5 2
6 4 3
Sample Output
3
2
HINT
对于第一组询问,满足条件的整数对有(2,2),(2,4),(4,2)。对于第二组询问,满足条件的整数对有(6,3),(3,3)。
Attention:为了方便书写,我们把x,y改成i,j,把多组数据的n改为T,把a,b改成n,m,并且我们让n<m
首先我们列出本题要求的柿子
\[\sum\limits_{i=1}^n\sum\limits_{j=1}^m[\gcd(i,j)=d]\]
d看起来太讨厌,我们把它直接除掉
\[\sum\limits_{i=1}^{\lfloor\frac{n}{d}\rfloor}\sum\limits_{j=1}^{\lfloor\frac{m}{d}\rfloor}[\gcd(i,j)=1]\]
然后我们发现最后面那一个长得和莫比乌斯函数很像,稍微改一下得到
\[\sum\limits_{i=1}^{\lfloor\frac{n}{d}\rfloor}\sum\limits_{j=1}^{\lfloor\frac{m}{d}\rfloor}\sum\limits_{x|i,x|j}\mu(x)\]
把枚举x的挪到前面
\[\sum\limits_{x=1}^{\lfloor\frac{n}{d}\rfloor}\mu(x)\lfloor\dfrac{n}{dx}\rfloor\lfloor\dfrac{m}{dx}\rfloor\]
这个柿子终于变得小清新了,但是如果直接枚举x的话还是摆脱不了TLE的命运。。。
注意到后面的\(\lfloor\dfrac{n}{dx}\rfloor\lfloor\dfrac{m}{dx}\rfloor\)在很多情况下值都是一样的,那么我们进行数论分块即可
总时间复杂度降为\(O(T\sqrt n)\)
/*program from Wolfycz*/
#include<cmath>
#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
#define inf 0x7f7f7f7f
using namespace std;
typedef long long ll;
typedef unsigned int ui;
typedef unsigned long long ull;
inline int read(){int x=0,f=1;char ch=getchar();for (;ch<'0'||ch>'9';ch=getchar()) if (ch=='-') f=-1;for (;ch>='0'&&ch<='9';ch=getchar()) x=(x<<1)+(x<<3)+ch-'0';return x*f;
}
inline void print(int x){if (x>=10) print(x/10);putchar(x%10+'0');
}
const int N=5e4;
int prime[N+10],miu[N+10],sum[N+10];
bool inprime[N+10];
void prepare(){miu[1]=1;int tot=0;for (int i=2;i<=N;i++){if (!inprime[i]) prime[++tot]=i,miu[i]=-1;for (int j=1;j<=tot&&i*prime[j]<=N;j++){inprime[i*prime[j]]=1;if (i%prime[j]==0){miu[i*prime[j]]=0;break;}miu[i*prime[j]]=-miu[i];}}for (int i=1;i<=N;i++) sum[i]=sum[i-1]+miu[i];
}
int main(){prepare();for (int Data=read();Data;Data--){int A=read(),B=read(),D=read();ll Ans=0;A/=D,B/=D;int x=min(A,B),pos=0;for (int d=1;d<=x;d=pos+1){pos=min(A/(A/d),B/(B/d));Ans+=1ll*(sum[pos]-sum[d-1])*(A/d)*(B/d);}printf("%lld\n",Ans);}return 0;
}
转载于:https://www.cnblogs.com/Wolfycz/p/9475395.html
浅谈算法——莫比乌斯反演相关推荐
- 浅谈算法和数据结构: 五 优先级队列与堆排序
原文:浅谈算法和数据结构: 五 优先级队列与堆排序 在很多应用中,我们通常需要按照优先级情况对待处理对象进行处理,比如首先处理优先级最高的对象,然后处理次高的对象.最简单的一个例子就是,在手机上玩游戏 ...
- 从石头剪刀布浅谈算法的作用
刚开始学习C语言的时候,常常听到前辈说,C语言的核心就是算法.但是对于小白来说,常常一脸懵逼,搞不懂啥叫算法?算法有什么用?我的if-else语句照样可以走天下.但是作为小白来说虽然不懂但是也不敢问, ...
- 【科技】浅谈圆的反演
一时兴起,就有了这篇博客.本人也学识浅薄,姑且讲一下我对于圆反演的一些皮毛之见. 首先我们要明白反演是什么: 反演是一种基本的几何变换.给定一个平面上的一个反演中心$O$和一个常数$k$,对于任意一个 ...
- 算法工程师_浅谈算法工程师的职业定位与发展
随着大数据和以深度学习为代表的人工智能技术的飞速发展,算法工程师这个职业逐渐成为国内互联网行业的标配.2016年3月,谷歌旗下DeepMind公司的围棋程序"AlphaGo"战胜职 ...
- 浅谈算法和数据结构: 七 二叉查找树
前文介绍了符号表的两种实现,无序链表和有序数组,无序链表在插入的时候具有较高的灵活性,而有序数组在查找时具有较高的效率,本文介绍的二叉查找树(Binary Search Tree,BST)这一数据结构 ...
- 浅谈算法(简单算法)
前言 算法(Algorithm)是指解题方案的准确而完整的描述,是一系列解决问题的清晰指令,算法代表着用系统的方法描述解决问题的策略机制.也就是说,能够对一定规范的输入,在有限时间内获得所要求的输出. ...
- 浅谈算法和数据结构: 哈希表
作者: yangecnu(yangecnu's Blog on 博客园) 出处:http://www.cnblogs.com/yangecnu/ http://www.cnblogs.com/yan ...
- 浅谈算法——多项式乘法相关
从多项式乘法到FFT 这一段大部分是复制以前我写的这篇博客: https://blog.csdn.net/wang3312362136/article/details/79510933 这篇博客有详细 ...
- 【算法笔记】莫比乌斯反演(包含定理,两种形式的证明及入门经典模板)
整理的算法模板合集: ACM模板 目录 一.莫比乌斯反演 二.几个概念和定理 三.两种形式的莫比乌斯反演证明 四.POJ 3904 Sky Code(入门例题) 一.莫比乌斯反演 学习笔记,我是看这个 ...
- 浅谈网络爬虫中广度优先算法和代码实现
前几天给大家分享了网络爬虫中深度优先算法的介绍及其代码实现过程,没来得及上车的小伙伴们可以戳这篇文章--浅谈网络爬虫中深度优先算法和简单代码实现.今天小编给大家分享网络爬虫中广度优先算法的介绍及其代码 ...
最新文章
- 记一个开发中遇到react-native flatList 的坑
- windows popen 获取不到输出_彻底明白os.system、os.popen、subprocess.popen的用法和区别...
- 到底什么成就了今天的人工智能?(上)
- 为什么HashMap会产生死循环?
- 输出第二个整数(信息学奥赛一本通-T1002)
- python函数参数值_python 函数参数
- Silverlight学习之贪吃蛇游戏
- 读取访问权限冲突怎么解决_CPU怎么保证内存访问冲突?一致性?
- 2.14.PHP7.1 狐教程-【PHP 静态类、静态方法、静态属性】
- 有DMX512协议控制的整套硬件解决方案吗?来看一下,舞台灯光同步视频播放DMX控制台
- 基于matlab 的燃油喷雾图像处理方法,基于matlab的燃油喷雾图像处理方法
- 每周经典电路分析:采样保持放大器(1)
- 知识表示-马尔科夫链(MC)
- 数论进阶——莫比乌斯反演
- win7系统激活最简单方法
- linux vi命令不能用,linux vi命令的使用方法
- 产品结构图 VS 信息结构图 VS 功能结构图(附案例)
- 【渝粤教育】广东开放大学 商务谈判 形成性考核 (34)
- 《高性能iOS 应用开发》之降低你 APP 的电量消耗
- Unity 安卓 Unable to initialize the Unity Engine / No Enough Space to install unity