zoukankan      html  css  js  c++  java
  • Codeforces Round #674 (Div. 3)

    比赛链接:https://codeforces.com/contest/1426

    A. Floor Number

    题意

    一所房子除第一层有 $2$ 个房间外其余层有 $x$ 个房间,给出房间号 $n$,问该房间在第几层。

    题解

    既然除了第一层外每层房间数都相等,那么只需计算在第一层的基础上还需加上几层即可,即 $1 + lceil frac{n-2}{x} ceil$ 。

    代码

    #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, x;
            cin >> n >> x;
            cout << 1 + (max(0, n - 2) + x - 1) / x << "
    ";
        }
        return 0;
    }

    B. Symmetric Matrix

    题意

    给出 $n$ 个 $2 imes 2$ 的小正方矩阵和大正方矩阵的边长 $m$,小矩阵每个位置有一个数,每个小矩阵使用次数不限,问能否用小矩阵完全填补大矩阵且大矩阵关于主对角线对称。

    题解

    只要至少有一个小矩阵关于主对角线对称即可,其次为了完全填补,大矩阵的边长需要为 $2$ 的倍数。

    代码

    #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, m;
            cin >> n >> m;
            bool ok = false;
            for (int i = 0; i < n; i++) {
                int a, b, c, d;
                cin >> a >> b >> c >> d;
                if (b == c) ok = true;
            }
            cout << (ok and m % 2 == 0 ? "YES" : "NO") << "
    ";
        }
        return 0;
    }

    C. Increase and Copy

    题意

    一开始数组中只有一个值为 $1$ 的数,每次操作可以选择:

    • 给一个数加一
    • 在末尾添加一个已有的数

    问使得所有数之和为 $n$ 的最少操作次数。

    题解

    $n = a imes b + c$,枚举 $a$ 即可。

    代码

    #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;
            cin >> n;
            int ans = INT_MAX;
            for (int i = 1; i * i <= n; i++) {
                ans = min(ans, (i - 1) + (n / i - 1) + (n % i != 0));
            }
            cout << ans << "
    ";
        }
        return 0;
    }

    D. Non-zero Segments

    题意

    计算使一个数组没有和为 $0$ 的连续区间至少要插入多少个数。

    题解

    计算前缀和,如果当前和在之前出现过,那么说明之前有一段和为 $0$ 的区间,插入一个数后清空之前的记录从当前数重新计算即可。

    代码

    #include <bits/stdc++.h>
    using namespace std;
    int main() {
        ios::sync_with_stdio(false);
        cin.tie(nullptr);
        int n;
        cin >> n;
        int ans = 0;
        set<long long> st;
        st.insert(0);
        long long sum = 0;
        for (int i = 0; i < n; i++) {
            int x;
            cin >> x;
            sum += x;
            if (st.count(sum)) {
                ++ans;
                st.clear();
                st.insert(0);
                st.insert(sum = x);
            } else {
                st.insert(sum);
            }
        }
        cout << ans << "
    ";
        return 0;
    }

    E. Rock, Paper, Scissors

    题意

    给出 $Alice$ 和 $Bob$ 各会出石头剪刀布的次数,问 $Alice$ 至少和至多会赢多少次。

    题解

    最多赢多少次比较好想,即 $min(a_1,b_2) + min(a_2,b_3) + min(a_3,b_1) $ 。

    最少赢多少次应考虑那些不得不赢的情况,即减去输掉和平局的所有局数后还有余的次数,可以证明这种情况最多只有一种。

    证明

    如果存在两个 $a_i - b_i - b_{i+2} > 0$,比如 $a_1 > b_1 + b_3$,$a_2 > b_2 + b_1$,那么 $a_1 + a_2 > b_1 + b_2 + b_3 + b_1 = n + b_1$,即 $a_1 + a_2 > n$,与 $a_1 + a_2 + a_3 = n$ 矛盾,所以不得不赢的情况至多只存在一种。

    代码

    #include <bits/stdc++.h>
    using namespace std;
    int main() {
        ios::sync_with_stdio(false);
        cin.tie(nullptr);
        int n;
        cin >> n;
        vector<int> a(3), b(3);
        for (auto &x : a) cin >> x;
        for (auto &x : b) cin >> x;
        int ans1 = 0, ans2 = 0;
        for (int i = 0; i < 3; i++) {
            ans1 = max(ans1, a[i] - b[(i + 2) % 3] - b[i]);
        }
        for (int i = 0; i < 3; i++) {
            ans2 += min(a[i], b[(i + 1) % 3]);
        }
        cout << ans1 << ' ' << ans2 << "
    ";
        return 0;
    }

    F. Number of Subsequences

    题意

    一个字符串由 $a,b,c$ 和 $k$ 个 $?$ 组成,$?$ 可以被替换为 $a,b,c$,问在 $3^k$ 个可能的字符串中共有多少个 $abc$ 序列。

    题解

    $dp_0$——字符串的个数

    $dp_1$——$a$序列的个数

    $dp_2$——$ab$序列的个数

    $dp_3$——$abc$序列的个数

    代码

    #include <bits/stdc++.h>
    using namespace std;
    constexpr int MOD = 1e9 + 7;
    int main() {
        ios::sync_with_stdio(false);
        cin.tie(nullptr);
        int n;
        cin >> n;
        string s;
        cin >> s;
        vector<long long> dp(4);
        dp[0] = 1;
        for (char c : s) {
            if (c == '?') {
                for (int i = 3; i > 0; i--) dp[i] = (dp[i] * 3 + dp[i - 1]) % MOD;
                dp[0] = dp[0] * 3 % MOD;            
            } else {
                int i = c - 'a' + 1;
                (dp[i] += dp[i - 1]) %= MOD;
            }
        }
        cout << dp[3] << "
    ";
        return 0;
    }

    参考博客

    https://blog.csdn.net/tomjobs/article/details/108858505

  • 相关阅读:
    【Anagrams】 cpp
    【Count and Say】cpp
    【Roman To Integer】cpp
    【Integer To Roman】cpp
    【Valid Number】cpp
    重构之 实体与引用 逻辑实体 逻辑存在的形式 可引用逻辑实体 不可引用逻辑实体 散弹式修改
    Maven项目聚合 jar包锁定 依赖传递 私服
    Oracle学习2 视图 索引 sql编程 游标 存储过程 存储函数 触发器
    mysql案例~tcpdump的使用
    tidb架构~本地化安装
  • 原文地址:https://www.cnblogs.com/Kanoon/p/13765639.html
Copyright © 2011-2022 走看看