zoukankan      html  css  js  c++  java
  • 2021暑假模拟赛3

    A[HDU6950(1200)]

    可以发现本质上相当于把$frac{N-1}{2}$所有空着的为$0$的位变成了$1$,求出最高位即可算出。

    #include <bits/stdc++.h>
    using namespace std;
    int main() {
      int T;
      cin >> T;
      while (T --> 0) {
        long long N;
        cin >> N;
        int B = 0;
        while ((1LL << B) <= (N - 1) / 2) {
          B ++;
        }
        cout << (1LL << B) - 1 << '
    ';
      }
    }
    View Code

    B[CF1404A(1500)]

    可以发现每个位置对$K$同余的位置都需要相同,也就是如果$i$ $mod$ $K=j$ $mod$ $K$,那么$S[i$ $mod$ $K]==S[j$ $mod$ $K]$。于是首先判断是否同一个同余系下的位置都相同,然后考虑$0$和$1$个数相等的条件,只需要看是否对于前$k$个位置存在一种改变$?$的方式使得$0$和$1$的个数相等。

    #include <bits/stdc++.h>
    
    using namespace std;
    
    int main() {
        ios::sync_with_stdio(false);
        cin.tie(nullptr);
    
        int T;
        cin >> T;
    
        while (T --) {
            int n, k;
            cin >> n >> k;
    
            string s;
            cin >> s;
    
            bool ok = true;
            for (int i = 0; i < n; ++i) {
                if (s[i] != '?') {
                    for (int j = i - k; j >= 0; j -= k) {
                        if (s[j] == '?') {
                            s[j] = s[i];
                        } else if (s[j] == s[i]) {
                            break;
                        } else {
                            ok = false;
                            break;
                        }
                    }
                    for (int j = i + k; j < n; j += k) {
                        if (s[j] == '?') {
                            s[j] = s[i];
                        } else if (s[j] == s[i]) {
                            break;
                        } else {
                            ok = false;
                            break;
                        }
                    }
                }
            }
    
            vector<vector<int> > pre(n + 1, vector<int> (2));
            for (int i = 0; i < n; ++i) {
                for (int j = 0; j < 2; ++j) {
                    pre[i + 1][j] = pre[i][j];
                }
                if (s[i] != '?') {
                    pre[i + 1][s[i] - '0'] ++;
                }
            }
            for (int i = 1; i <= n; ++i) {
                if (i >= k) {
                    if (pre[i][0] - pre[i - k][0] > k / 2 || pre[i][1] - pre[i - k][1] > k / 2) {
                        ok = false;
                    }
                }
            }
    
            if (ok) {
                cout << "YES" << '
    ';
            } else {
                cout << "NO" << '
    ';
            }
        }
    
        return 0;
    }
    View Code

    C[CF1458A(1600)]

    看见这个形式会联想到辗转相减法$gcd(A,B)=gcd(B,A-B)$,将剩余的项都减去第一项,变成$gcd(A_1+B_j,A_2-A_1,...,A_N-A_1)$。发现只有第一项是变的,于是先将后面定值预处理出来再每次单独$gcd$即可。

    #include <bits/stdc++.h>
    using namespace std;
    int main() {
      int N, M;
      cin >> N >> M;
      vector<long long> A(N);
      for (int i = 0; i < N; ++i) {
        cin >> A[i];
      }
      vector<long long> B(M);
      for (int i = 0; i < M; ++i) {
        cin >> B[i];
      }
      long long g = 0;
      for (int i = 0; i < N - 1; ++i) {
        g = __gcd(g, A[i] - A[i + 1]);
      }
      for (int i = 0; i < M; ++i) {
        cout << abs(__gcd(g, A[0] + B[i])) << " 
    "[i == M - 1];
      }
    }
    View Code

    D[CF1466E(1800)]

    看到这个式子发现跟$j$关系较大,于是将$j$提到前面,然后其他两项可以分开来算。于是先枚举$j$,然后按位枚举,先预处理这一位在所有$X$中出现的次数,根据$and$和$or$的性质进行简单的讨论即可。

    #include <bits/stdc++.h>
    
    using namespace std;
    
    const int P = 1000000000 + 7;
    
    int main() {
        ios::sync_with_stdio(false);
        cin.tie(nullptr);
    
        int T;
        cin >> T;
    
        while (T --) {
            int n;
            cin >> n;
    
            vector<long long> x(n);
            for (int i = 0; i < n; ++i) {
                cin >> x[i];
            }
    
            vector<long long> cnt(61);
            for (int i = 0; i < n; ++i) {
                for (int j = 0; j < 61; ++j) {
                    if (x[i] >> j & 1) {
                        cnt[j] ++;
                    }
                }
            }
    
            long long ans = 0;
            for (int j = 0; j < n; ++j) {
                long long sa = 0;
                for (int b = 0; b < 61; ++b) {
                    if (x[j] >> b & 1) {
                        sa = (sa + (1LL << b) % P * cnt[b] % P) % P;    
                    }
                }    
                long long sb = 0;
                for (int b = 0; b < 61; ++b) {
                    if (x[j] >> b & 1) {
                        sb = (sb + (1LL << b) % P * n % P) % P;    
                    } else {
                        sb = (sb + (1LL << b) % P * cnt[b] % P) % P;
                    }
                }
                ans = (ans + sa * sb) % P;
            }
    
            cout << ans << '
    ';
        }
    
        return 0;
    }
    View Code
  • 相关阅读:
    一分钟搞懂列式与行式数据库(转)
    docker daemon 配置文件
    Docker-删除untagged docker images
    全栈JavaScript之路(十三)了解 ElementTraversal 规范
    static, readonly, const
    Timer与AlarmManager的差别
    计算客 (人人都有极客精神)爆力
    nginx 配置web 虚拟文件夹 而且codeIgniter,thinkphp 重定向url 地址
    单例模式之 懒汉模式普通版
    POJ 3468 A Simple Problem with Integers 【树状数组】
  • 原文地址:https://www.cnblogs.com/19992147orz/p/15077196.html
Copyright © 2011-2022 走看看