[POI2007]ZAP-Queries



$ solution: $

唉,数论实在有点烂了,昨天还会的,今天就不会了,周末刚证明的,今天全忘了,还不如早点写好题解。

这题首先我们可以列出来答案就是:

$ ans=\sum_{i=1}{a}{\sum_{j=1}{b}{[gcd(i,j)==d]}} $

我们发现后面那个东西(只有 $ gcd(i,j)d $ 时才为一)跟莫比乌斯很像,莫比乌斯是(只有 $ n $ 1 才为一),所以我们再尝试转化一下(把d转化成1):

$ ans=\sum_{i=1}{\frac{a}{d}}{\sum_{j=1}{\frac{b}{d}}{[gcd(i,j)==1]}} $

于是我们就可以把后面那个东西用莫比乌斯函数的第一条性质转换成这样:

$ ans=\sum_{i=1}{\frac{a}{d}}{\sum_{j=1}{\frac{b}{d}}{\sum_{k|gcd(i,j)}{\mu(k)}}} $

但是这样显然还不够,我们想办法把莫比乌斯的式子挪到前面去:

$ ans=\sum_{k}{min(a,b)}{\mu(k)}{\sum_{i=1}{\frac{a}{d}}{\sum_{j=1}^{\frac{b}{d}}{[k|gcd(i,j)]}}} $

这个其实就相当于我们从小到大枚举k,但是我们是从上面那个式子转化过来的,所以必须满足 $ [k|gcd(i,j)] $ 这个条件。好了,现在我们肉眼观察一下,发现如下的东西:

$ {\sum_{i=1}{\frac{a}{d}}{\sum_{j=1}{\frac{b}{d}}{[k|gcd(i,j)]}}}=\lfloor \frac{\lfloor \frac{a}{d} \rfloor}{k} \rfloor \times \lfloor \frac{\lfloor \frac{b}{d} \rfloor}{k} \rfloor=\lfloor \frac{a}{d\times k} \rfloor \times \lfloor \frac{b}{d\times k} \rfloor $

$ ans=\sum_{k}^{min(a,b)}{\mu(k)\times \lfloor \frac{a}{d\times k} \rfloor \times \lfloor \frac{b}{d\times k} \rfloor} $

然后我们发现这样子的复杂度是 $ O(min(a,b)) $ 的,然而它的询问次数太多。于是出现了一个很奇妙的东西:整除分块(又叫数论分块)。举个栗子:

$ \frac{10}{1}=10 $

$ \frac{10}{2}=5 $

$ \frac{10}{3}=3 $

$ \frac{10}{4}=\frac{10}{5}=2 $

$ \frac{10}{6}=\frac{10}{7}=\frac{10}{8}=\frac{10}{9}=\frac{10}{10}=1 $

我们发现分子相同分母越大,则出现相同结果的概率越高,所以我们可以一次求出某一段相同结果的左端点和右端点(假设这一段的结果都为y,则这一段的最右端就是用分子除以y得到的值),从而使算法效率变高,这就是整除分块。



$ code: $

#include<iostream>
#include<cstdio>
#include<iomanip>
#include<algorithm>
#include<cstring>
#include<cstdlib>
#include<ctime>
#include<cmath>
#include<vector>
#include<queue>
#include<map>
#include<set> #define ll long long
#define db double
#define inf 0x7fffffff
#define rg register int using namespace std; int Q;
int pr[50005];
int mu[50005];
bool use[50005]; inline int min(const rg &x,const rg &y){
if(x<y)return x; else return y;
} inline int qr(){
register char ch; register bool sign=0; rg res=0;
while(!isdigit(ch=getchar())) if(ch=='-')sign=1;
while(isdigit(ch)) res=res*10+(ch^48),ch=getchar();
return sign?-res:res;
} inline void get_mu(int x){
rg t=0; mu[1]=1;
for(rg i=2;i<=x;++i){
if(!use[i])mu[i]=-1,pr[++t]=i;
for(rg j=1;j<=t;++j){
if(i*pr[j]>x)break;
use[i*pr[j]]=1;
if(!(i%pr[j]))break;
else mu[i*pr[j]]=-mu[i];
}
}
for(rg i=2;i<=x;++i) mu[i]+=mu[i-1];
} int main(){
//freopen(".in","r",stdin);
//freopen(".out","w",stdout);
Q=qr();
get_mu(50000);
while(Q--){
rg a=qr(),b=qr(),k=qr();
a/=k; b/=k;
rg r,n=min(a,b),ans=0;
for(rg l=1;l<=n;l=r+1){
r=min(a/(a/l),b/(b/l));
ans+=((a/l)*(b/l)*(mu[r]-mu[l-1]));
}printf("%d\n",ans);
}
return 0;
}

[POI2007]ZAP-Queries (莫比乌斯反演+整除分块)的更多相关文章

  1. [P4450] 双亲数 - 莫比乌斯反演,整除分块

    模板题-- \[\sum\limits_{i=1}^a\sum\limits_{j=1}^b[(i,j)=k] = \sum\limits_{i=1}^a\sum\limits_{j=1}^b[k|i ...

  2. Bzoj1101: [POI2007]Zap 莫比乌斯反演+整除分块

    题目:https://www.lydsy.com/JudgeOnline/problem.php?id=1101 莫比乌斯反演 1101: [POI2007]Zap 设 \(f(i)\) 表示 \(( ...

  3. 莫比乌斯反演&整除分块学习笔记

    整除分块 用于计算$\sum_{i=1}^n f(\lfloor{n/i} \rfloor)*i$之类的函数 整除的话其实很多函数值是一样的,对于每一块一样的商集中处理即可 若一个商的左边界为l,则右 ...

  4. 洛谷 P2257 - YY的GCD(莫比乌斯反演+整除分块)

    题面传送门 题意: 求满足 \(1 \leq x \leq n\),\(1 \leq y \leq m\),\(\gcd(x,y)\) 为质数的数对 \((x,y)\) 的个数. \(T\) 组询问. ...

  5. 【BZOJ1101】[POI2007] Zap(莫比乌斯反演)

    点此看题面 大致题意: 求\(\sum_{x=1}^N\sum_{y=1}^M[gcd(x,y)==d]\). 一道类似的题目 推荐先去做一下这道题:[洛谷2257]YY的GCD,来初步了解一下莫比乌 ...

  6. 洛谷 - P2257 - YY的GCD - 莫比乌斯反演 - 整除分块

    https://www.luogu.org/problemnew/show/P2257 求 \(n,m\) 中 \(gcd(i,j)==p\) 的数对的个数 求 $\sum\limits_p \sum ...

  7. [国家集训队] Crash的数字表格 - 莫比乌斯反演,整除分块

    考虑到\(lcm(i,j)=\frac{ij}{gcd(i,j)}\) \(\sum_{i=1}^n\sum_{j=1}^m\frac{ij}{gcd(i,j)}\) \(\sum_{d=1}^{n} ...

  8. 洛谷 P5518 - [MtOI2019]幽灵乐团 / 莫比乌斯反演基础练习题(莫比乌斯反演+整除分块)

    洛谷题面传送门 一道究极恶心的毒瘤六合一题,式子推了我满满两面 A4 纸-- 首先我们可以将式子拆成: \[ans=\prod\limits_{i=1}^A\prod\limits_{j=1}^B\p ...

  9. P2568 莫比乌斯反演+整除分块

    #include<bits/stdc++.h> #define LL long long using namespace std; ; bool vis[maxn]; int prime[ ...

随机推荐

  1. mybatis 一对多的注入 指的是连表查询时候 将不同的查询结果以列表存储对象形式 注入进去 多对一指的是 查询多条结果但都是一样的 只需注入一条

    mybatis 一对多的注入 指的是连表查询时候 将不同的查询结果以列表存储对象形式 注入进去 多对一指的是 查询多条结果但都是一样的 只需注入一条

  2. BZOJ2553[BeiJing2011]禁忌——AC自动机+概率DP+矩阵乘法

    题目描述 Magic Land上的人们总是提起那个传说:他们的祖先John在那个东方岛屿帮助Koishi与其姐姐Satori最终战平.而后,Koishi恢复了读心的能力…… 如今,在John已经成为传 ...

  3. BZOJ1367 BOI2004Sequence(左偏树)

    首先考虑把bi和ai同时减i,问题变为非严格递增.显然如果a是一个递减序列,b序列所有数都取其中位数最优.于是划分原序列使得每一部分递减,然后考虑合并相邻两段.如果前一段的中位数<=后一段的中位 ...

  4. java 获取 T.class

    转载:http://www.hankcs.com/program/t-class.html @Test public void Test() throws Exception{ Foo<User ...

  5. P2577 [ZJOI2005]午餐

    题目描述 上午的训练结束了,THU ACM小组集体去吃午餐,他们一行N人来到了著名的十食堂.这里有两个打饭的窗口,每个窗口同一时刻只能给一个人打饭.由于每个人的口味(以及胃口)不同,所以他们要吃的菜各 ...

  6. 【ZOJ2276】Lara Croft(bfs)

    BUPT2017 wintertraining(16) #4 D ZOJ - 2276 题意 n个数字绕成环,有两个指示数字的方块,每次可以顺时针或逆时针移动其中一个,步数是它当前位置的数字a[i], ...

  7. PHP 判断浏览器语言

    详情请参看代码 作用:判断当前的浏览器语言.接收传入参数.拼接字符串 <?php $lang = substr($_SERVER['HTTP_ACCEPT_LANGUAGE'],0,2); if ...

  8. django MTV架构下的网站开发步骤

    1.需求分析必不可少,一定要具体列出本次网站项目所要实现的目标,可能包括简单的页面草图与功能方块图等. 2.数据库设计. 3.了解网站的每一个页面,并设计网页模板(.html)文件 4.使用virtu ...

  9. AAD Service Principal获取azure user list (Microsoft Graph API)

    本段代码是个通用性很强的sample code,不仅能够操作AAD本身,也能通过Azure Service Principal的授权来访问和控制Azure的订阅资源.(Azure某种程度上能看成是两个 ...

  10. Azure登陆的两种常见方式(user 和 service principal登陆)

    通过Powershell 登陆Azure(Azure MoonCake为例)一般常见的有两种方式 1. 用户交互式登陆 前提条件:有一个AAD account 此种登陆方式会弹出一个登陆框,让你输入一 ...