UVA 10325 The Lottery(容斥原理)

传送门


UVA 10325 The Lottery(容斥原理)_第1张图片

题目大意:

就是给定一个数 n,m,还有m个数a[i],然后让你求的就是在 1- n中 没有被这m个数整除的个数...

解析样例:

10 2

 2  3

在1-10中2的倍数有A={ 2 4 6  8 10},3的倍数有B={3 6 9},2和3的最小公倍数C={6},所以 就是A+B-C == 7;

然后所求结果 ret == 10 - 7 == 3


解题思路:

由上述样例解析也可以知道 这是一个容斥原理的题目,我们要求的就是将所有的a[i]的倍数去掉,我们要求的是个数,所以 只需要用 n/LCM(...)就行了,但是其中有很多重复的,a[i]和a[j]的最小公倍数就是重复的,所以我们还要进行去重,就是容斥原理,在进行一下 二进制枚举,最后判断奇偶,奇加偶减。


My Code:

#include <iostream>
#include <cstdio>
using namespace std;
typedef long long  LL;
LL arr[20];
LL GCD(LL m, LL n)
{
    if(n == 0)
        return m;
    return GCD(n, m%n);
}
LL lcm(LL a, LL b)
{
    LL t = GCD(a, b);
    return a/t*b;
}
int main()
{
    LL n,m;
    while(cin>>n>>m)
    {
        for(int i=0; i<m; i++)
            cin>>arr[i];
        LL sum = 0;
        for(int i=1; i<(1<<m); i++)///二进制枚举集合所有情况
        {
            LL ans = 1;
            int cnt = 0;///集合中元素个数
            for(int j=0; j<m; j++)
            {
                if(i & (1<<j))
                {
                    ans = lcm(ans,arr[j]);
                    if(ans > n)
                        break;
                    cnt++;
                }
            }
            if(cnt & 1)///奇加
                sum += n/ans;
            else///偶减
                sum -= n/ans;
        }
        cout<<n-sum<<endl;
    }
    return 0;
}


你可能感兴趣的:(UVA 10325 The Lottery(容斥原理))