• Lucky 7 (容斥原理 + 中国剩余定理)


    题意:求满足7的倍数,不满足其他条件num % p == a 的num的个数。

    思路:利用中国剩余定理我i们可以求出7的倍数,但是多算了不满足约定条件又得减去一个,但是又发现多减了,又得加回来。如此,那么应该应用容斥原理来解决问题。那么就应该是将所有的状态都遍历一下,然后根据1的个数来判断是不是+-号。

    #include<bits/stdc++.h>
    using namespace std;
    typedef long long ll;
    
    const int maxn = 30;
    ll n, l, r;
    ll m[maxn], a[maxn], f[maxn];
    
    ll ex_gcd(ll a, ll b, ll &x, ll &y) {
        if(!b) {
            x = 1;
            y = 0;
            return a;
        } else {
            ll tmp = ex_gcd(b, a%b, y, x);
            y -= a / b * x;
            return tmp;
        }
    }
    
    inline ll cnt(ll k, ll m, ll x) {
        return (m - k + x) / m;
    }
    
    ll mul(ll a, ll b, ll m) {
        ll ans = 0;
        while(b) {
            if(b&1LL) {
                ans += a;
                ans %= m;
            }
            a <<= 1;
            a %= m;
            b >>= 1;
        }
        return ans;
    }
    ll crt(int n, ll l, ll r) {
        ll M = 1;
        for(int i = 0; i < n; i++)
            if(f[i])
                M *= m[i];
    
        ll ans = 0;
        for(int i = 0; i < n; i++)
            if(f[i]) {
                ll mi = M / m[i];
                ll mf, tmp;
                ex_gcd(mi, m[i], mf, tmp);
                mf = (mf % m[i] + m[i]) % m[i];
    
                ans += mul(mul(a[i], mi, M), mf, M);
                ans = (ans % M + M) % M;
            }
        return cnt(ans, M, r) - cnt(ans, M, l-1);
    }
    
    int main() {
        int T;
        scanf("%d", &T);
        for(int ncase = 1; ncase <= T; ncase ++) {
            scanf("%lld%lld%lld", &n, &l, &r);
            for(int i = 0; i < n; i ++) {
                scanf("%lld%lld", &m[i], &a[i]);
            }
            ll ans = 0;
            m[n] =7; a[n] = 0; f[n] = 1;
            for(int i = 0; i < (1 << n); i ++){
                int tmp = i, cn = 0;
                for(int j = 0; j < n; j ++){
                    if(tmp & 1) {
                        f[j] = 1; cn ++;
                    }else{
                        f[j] = 0;
                    }
                    tmp >>= 1;
                }
                if(cn & 1) ans -= crt(n + 1, l, r);
                else ans += crt(n + 1, l, r);
            }
            printf("Case #%d: %lld
    ",ncase,ans);
        }
        return 0;
    }
    more crazy more get!
  • 相关阅读:
    Spring Boot 配置元数据指南
    面试中常被提到的最左前缀匹配原则
    MyBatis缓存机制(一级缓存,二级缓存)
    计算机网络基础知识
    垃圾收集算法与垃圾收集器
    递归与分治策略
    五种IO模型和BIO,NIO,AIO
    七种阻塞队列
    ConcurrentHashMap(1.7版本和1.8版本)
    重入锁 ReentrantLock
  • 原文地址:https://www.cnblogs.com/wethura/p/9861466.html
Copyright © 2020-2023  润新知