大致思路就是先求出n的质因数假设是a1-an,然后在1-a的区间里面查找至少能整除{a1,a2...an}中一个元素的数有多少个,对1-b也做相同的处理,而找出来的元素肯定是与n不互质的,那么把区间的长度减去元素的个数就是那个区间里面与n互质的数的个数了,然后1-b的减去1-(a-1)的就是答案了。

而在1-a的区间里面查找至少能整除{a1,a2...an}中一个元素的数有多少个,这里就要用到容斥原理了。

首先来看容斥原理

计数时,必须注意没有重复,没有遗漏。为了使重叠部分不被重复计算,人们研究出一种新的计数方法,这种方法的基本思想是:先不考虑重叠的情况,把包含于某内容中的所有对象的数目先计算出来,然后再把计数时重复计算的数目排斥出去,使得计算的结果既无遗漏又无重复,这种计数的方法称为容斥原理。

就比如质因数有2,3 然后1-10里面能整除2的有2,4,6,8,10;能整除3的有3,6,9;把这个看作成集合A,集合B,|A∩B|=1,|A|=5,|B|=3,|A∪B|=|A|+|B|-|A∩B|;

将这个公式推广到n个集合

回到题目,考虑质因子{a1,a2,a3..an},那么在[1-r]有多少个数能整除ai,答案就是[r/ai],但是单纯的把答案加上去肯定是错的(有些数可能被好几个质因子整除),这个时候就用到容斥原理来解决。

假设有m个质因子,那么就有2^m-1种情况(lcm(...),中间填入数字,每个数字都有两种选择,填还是不填,但不能全部都不填对吧);

附上模板

int solve (ll n, ll r)
{ vector<ll> p;
p.clear();
for (int i=; i*i<=n; ++i)
if (n % i == )
{
p.push_back (i);
while (n % i == )
n /= i;
}
if (n > )
p.push_back (n);
//分解质因数
ll sum = ;
ll cur;
ll mult = ;
ll bits = ;
ll s=<<p.size();
for (ll msk=; msk<s; msk++)
{ mult = ;
bits = ;
for (int i=; i<p.size(); ++i)
if (msk & (<<i))
{
bits++;
mult *= p[i]; }
cur = r / mult;
if (bits % == )
sum += cur;
else
sum -= cur; }
//printf("%lld\n",sum);
return r - sum;//1-r与n互质的数的个数 }

我把模板里面的位运算解释一下吧,p.size()代表n的质因数有多少个,而1<<p.size()就是2^(p.size()),mult表示某几个质因数的最小公倍数,bits表示集合的个数,用msk把1->p.size()-1里面所有的数用二进制表示出来,而if(a&b)表示a和b的二进制表示有没有相同的一位都为1,如果有就为真,没有就为假,现在假如有一个数30,那么它的质因数有2,3,5,那么一共有001,010,011,100,101,110,111,这七种情况,在里面的第二个循环其实就是为了读取msk的二进制有哪几位是1,因为二进制把所有的情况都包括了,就比如001,001&001=1,其他的都为假,这个时候就读到了|A1|这种情况,即2,里面的循环1<<i,只能得到001,010,100这几个数,010&010=1,其他的都为假,这个时候就读到了|A2|这种情况,即3,011&001=1,011&010=1,这个时候就读取到了|A1∩A2|的情况,即2,3的最小公倍数即6,而由于容斥原理当里面的集合有偶数个的时候是要减去这个集合里面元素的数量的,所以这个时候就知道了|A1|+|A2|-|A1∩A2|,

100&100=1,这个时候读到了|A3|,

101&001=1,101&100=1,这个时候读到了|A1∩A3|,

110&100=1,110&010=1,这个时候读到了|A2∩A3|,

111&001=1,111&010=1,111&100=1,这个时候读到了|A1∩A2∩A3|,

到这个时候所有的情况已经全部都读取完毕了,然后按照在[1-r]有多少个数能整除ai,答案就是[r/ai]这种性质,就能求出每个集合里面元素的数量,然后按照容斥原理的公式相加减就好了。

那么答案就是套模板了

#include <stdio.h>
#include <iostream>
#include <vector>
using namespace std;
typedef long long ll;
vector<ll> p;
int solve (ll n, ll r)
{ p.clear();
for (int i=; i*i<=n; ++i)
if (n % i == )
{
p.push_back (i);
while (n % i == )
n /= i;
}
if (n > )
p.push_back (n);
//分解质因数
ll sum = ;
ll cur;
ll mult = ;
ll bits = ;
ll s=<<p.size();
for (ll msk=; msk<s; msk++)
{ mult = ;
bits = ;
for (int i=; i<p.size(); ++i)
if (msk & (<<i))
{
bits++;
mult *= p[i]; }
cur = r / mult;
if (bits % == )
sum += cur;
else
sum -= cur; }
//printf("%lld\n",sum);
return r - sum;//1-r与n互质的数的个数 }
int main()
{
ll a,b,n;
int t;
scanf("%d",&t);
while(t--)
{
scanf("%lld %lld %lld",&a,&b,&n);
ll r=solve(n,b);
ll l=solve(n,a-);
printf("%lld\n",r-l); }
}

南理第八届校赛同步赛-C count_prime//容斥原理的更多相关文章

  1. 南理第八届校赛同步赛-F sequence//贪心算法&二分查找优化

    题目大意:求一个序列中不严格单调递增的子序列的最小数目(子序列之间没有交叉). 这题证明贪心法可行的时候,可以发现和求最长递减子序列的长度是同一个方法,只是思考的角度不同,具体证明并不是很清楚,这里就 ...

  2. 哈尔滨理工大学软件与微电子学院第八届程序设计竞赛同步赛(高年级) Solution

    A: Solved. 分别处理出每个%7后余数的数字个数,再组合一下 #include <bits/stdc++.h> using namespace std; #define ll lo ...

  3. NOIP2013,复赛及同步赛,报名及比赛,专题页面

    本通知的对象仅仅是福州第十九中学的学生 所有参加复赛以及同步赛的选手,请务必要仔细阅读:<关于CCF NOIP2013复赛有关事宜的通知>,里面有比赛的时间.地点.以及比赛费用的说明. 参 ...

  4. 山东省ACM多校联盟省赛个人训练第六场 poj 3335 D Rotating Scoreboard

    山东省ACM多校联盟省赛个人训练第六场 D Rotating Scoreboard https://vjudge.net/problem/POJ-3335 时间限制:C/C++ 1秒,其他语言2秒 空 ...

  5. Minieye杯第十五届华中科技大学程序设计邀请赛现场同步赛 I Matrix Again

    Minieye杯第十五届华中科技大学程序设计邀请赛现场同步赛 I Matrix Again https://ac.nowcoder.com/acm/contest/700/I 时间限制:C/C++ 1 ...

  6. NOI Day1线上同步赛梦游记

    Preface 第一次体验NOI,虽然不是正式选手,但是打打同步赛还是挺涨姿势的,也算是体验了一把. Day1很爆炸,一方面是NOI题目的难度高于自身的水平,另一方面也出现了比较大的失误,T1一个数组 ...

  7. NOI 2018网络同步赛(游记?)

    刚中考完那段时间比较无聊,报名了一个同步赛,报完名才发现成绩单是要挂到网上的,而且因为报的早给了一个很靠前的考号...那布星啊,赶紧学点东西,于是在一周内学了网络流,Treap以及一些数论. Day1 ...

  8. 10.17(山东多校联合模拟赛 day1)

    山东多校联合模拟赛 day1 题不难 rect [问题描述] 给出圆周上的 N 个点, 请你计算出以这些点中的任意四个为四个角,能构成多少个矩形. 点的坐标是这样描述的, 给定一个数组 v[1..N] ...

  9. 【NOI 2019】同步赛 / 题解 / 感想

    非常颓写不动题怎么办…… 写下这篇博客警示自己吧…… 游记 7.16 我并不在广二参加 NOI,而是在距离广二体育馆一公里远的包间打同步赛(其实就是给写不动题找个理由) 上午身体不舒服,鸽了半天才看题 ...

随机推荐

  1. hibernate多对多的更新问题

    错误原因 A different ]; nested exception ]] with root cause org.hibernate.NonUniqueObjectException: A di ...

  2. (Beta)Let's-M2后分析报告

    设想和目标 1. 我们的软件要解决什么问题?是否定义得很清楚?是否对典型用户和典型场景有清晰的描述? 在M1阶段我们对用户需求进行了调研,同时M1阶段我们的开发目标就是为了解决用户发起.参与.查看.搜 ...

  3. Nice Garland CodeForces - 1108C (思维+暴力)

    You have a garland consisting of nn lamps. Each lamp is colored red, green or blue. The color of the ...

  4. Mike and distribution CodeForces - 798D (贪心+思维)

    题目链接 TAG: 这是我近期做过最棒的一道贪心思维题,不容易想到,想到就出乎意料. 题意:给定两个含有N个正整数的数组a和b,让你输出一个数字k ,要求k不大于n/2+1,并且输出k个整数,范围为1 ...

  5. YCSB报": No such file or directory"异常

    异常信息如下: 文件路径.权限都没有问题. 上网遍寻无果,安装流程与官网一致,开始怀疑是环境问题,后来用别人能用的YCSB复制到本地,却能正常运行. 后来修改了ycsb文件,加了个空格,保存退出,再运 ...

  6. linux如何查看所有的用户(user)、用户组(group)、密码(password/passwd)

    linux如何查看所有的用户和组信息_百度经验https://jingyan.baidu.com/article/a681b0de159b093b184346a7.html linux添加用户.用户组 ...

  7. .net 报错汇总——持续更新

    1.未能找到 CodeDom 提供程序类型“Microsoft.CodeDom.Providers.DotNetCompilerPla PM> Install-Package Microsoft ...

  8. Oracle pivot行转列函数案例

    with temp as( select '湖北省' province,'武汉市' city,'第一' ranking from dual union all select '湖北省' provinc ...

  9. 转《service worker在移动端H5项目的应用》

    1. PWA和Service Worker的关系 PWA (Progressive Web Apps) 不是一项技术,也不是一个框架,我们可以把她理解为一种模式,一种通过应用一些技术将 Web App ...

  10. ConnectTimeout和ReadTimeout所代表的意义

    参考:ConnectTimeout和ReadTimeout所代表的意义 ConnectTimeout 指的是建立连接所用的时间,适用于网络状况正常的情况下,两端连接所用的时间. 在java中,网络状况 ...