博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
Luogu P3172 [CQOI2015]选数
阅读量:5328 次
发布时间:2019-06-14

本文共 1186 字,大约阅读时间需要 3 分钟。

这题的反演做法好像很不可食用啊还得套一个杜教筛

我们注意到题目一个重要的性质:\(H-L\le10^5\),看起来可以好好利用一下。

我们首先转化问题,类似于许多和\(\gcd\)有关的问题,我们将原来的最大公约数\(K\)想办法变成\(1\)

这个怎么处理呢,其实很简单,将\(L\)变为\(\lceil \frac{L}{K}\rceil\),将\(R\)变为\(\lfloor\frac{H}{K}\rfloor\)

显然这样我们把问题转化为:在\([L,H]\)种取\(N\)次数使它们的\(\gcd\)\(1\)

然后我们考虑计算一个\(f_i\),表示选出的数的\(\gcd\)\(i\),且选出的所有数不全相同的方案数。

那么我们借的思路,考虑容斥计算\(f_i\)

我们首先求出\([L,H]\)之间\(i\)的倍数\(x\),那么先令\(f_i=x^N-x\)

但是发现这样的方案只是含有公约数,因此我们还要减去\(f_{ki}(k\in N^+,k>1)\)的答案

然后做法很明显了,倒序枚举并计算即可,复杂度根据调和级数公式为\(O(n(\ln(n)+H_n))\)

还有注意一下\(L=1\)时所有的数都可以选\(1\),因此要特判。

CODE

#include
#define RI register intusing namespace std;const int N=100005,mod=1000000007;int n,k,L,R,l,r,f[N];inline void dec(int &x,int y){ if ((x-=y)<0) x+=mod;}inline int quick_pow(int x,int p,int mul=1){ for (;p;p>>=1,x=1LL*x*x%mod) if (p&1) mul=1LL*mul*x%mod; return mul;}int main(){ RI i,j; scanf("%d%d%d%d",&n,&k,&L,&R); L=L%k?L/k+1:L/k; R=R/k; for (i=1;i<=R-L;++i) { int l=L%i?L/i+1:L/i,r=R/i; f[i]=quick_pow(r-l+1,n); dec(f[i],r-l+1); } for (i=R-L;i;--i) for (j=i<<1;j<=R-L;j+=i) dec(f[i],f[j]); return printf("%d",L^1?f[1]:(f[1]+1)%mod),0;}

转载于:https://www.cnblogs.com/cjjsb/p/9873492.html

你可能感兴趣的文章
windows 安装yaml支持和pytest支持等
查看>>
读书笔记:季羡林关于如何做研究学问的心得
查看>>
面向对象的优点
查看>>
套接口和I/O通信
查看>>
阿里巴巴面试之利用两个int值实现读写锁
查看>>
浅谈性能测试
查看>>
Winform 菜单和工具栏控件
查看>>
CDH版本大数据集群下搭建的Hue详细启动步骤(图文详解)
查看>>
巧用Win+R
查看>>
浅析原生js模仿addclass和removeclass
查看>>
Python中的greenlet包实现并发编程的入门教程
查看>>
java中遍历属性字段及值(常见方法)
查看>>
深入理解jQuery框架-框架结构
查看>>
YUI3自动加载树实现
查看>>
python知识思维导图
查看>>
当心JavaScript奇葩的逗号表达式
查看>>
App Store最新审核指南(2015年3月更新版)
查看>>
织梦MIP文章内容页图片适配百度MIP规范
查看>>
点击复制插件clipboard.js
查看>>
[Kali_BT]通过低版本SerialPort蓝牙渗透功能手机
查看>>