比赛链接:Here

AB水题,

C - Many Balls

题意:

  • 现在有一个数初始为 AtCoder Beginner Contest 216 - 图1#card=math&code=0%28x%29) 以及两种操作

    1. 操作 AtCoder Beginner Contest 216 - 图2 AtCoder Beginner Contest 216 - 图3
    2. 操作 AtCoder Beginner Contest 216 - 图4

AtCoder Beginner Contest 216 - 图5 现在给你一个数 AtCoder Beginner Contest 216 - 图6 ,问如何通过以上操作将 AtCoder Beginner Contest 216 - 图7 变成 AtCoder Beginner Contest 216 - 图8 ,操作数不超过 AtCoder Beginner Contest 216 - 图9

思路:

AtCoder Beginner Contest 216 - 图10 保证一定有解

首先我们肯定是操作AtCoder Beginner Contest 216 - 图11 使得 AtCoder Beginner Contest 216 - 图12 不然执行操作 AtCoder Beginner Contest 216 - 图13 无意义

接下来尽可能使得 AtCoder Beginner Contest 216 - 图14 接近 AtCoder Beginner Contest 216 - 图15 也就是多执行操作AtCoder Beginner Contest 216 - 图16

接下来就是补 AtCoder Beginner Contest 216 - 图17

  1. int main() {
  2. cin.tie(nullptr)->sync_with_stdio(false);
  3. ll n;
  4. cin >> n;
  5. stack<char>st;
  6. while (n) {
  7. while (n % 2 == 0) {
  8. n /= 2;
  9. st.push('B');
  10. }
  11. while (n % 2 != 0) {
  12. n -= 1;
  13. st.push('A');
  14. }
  15. }
  16. while (!st.empty()) {
  17. cout << st.top();
  18. st.pop();
  19. }
  20. }

思路二:

用二进制的眼光看数字。对一个二进制数字来说要增加一个 AtCoder Beginner Contest 216 - 图18 就要乘 AtCoder Beginner Contest 216 - 图19 ,增加一个 AtCoder Beginner Contest 216 - 图20 就要乘 AtCoder Beginner Contest 216 - 图21AtCoder Beginner Contest 216 - 图22 。从高位到低位看数字 AtCoder Beginner Contest 216 - 图23 ,第一个出现 AtCoder Beginner Contest 216 - 图24 的位置就是一开始的加 AtCoder Beginner Contest 216 - 图25 ,然后剩下的位置中,如果是 AtCoder Beginner Contest 216 - 图26 ,就一定是AtCoder Beginner Contest 216 - 图27 得到的,是 AtCoder Beginner Contest 216 - 图28 就是 AtCoder Beginner Contest 216 - 图29 得到的。

【AC Code】

  1. int a[120];
  2. int main() {
  3. cin.tie(nullptr)->sync_with_stdio(false);
  4. ll n;
  5. cin >> n;
  6. int cnt = 0;
  7. while (n) {
  8. a[cnt ++] = n % 2;
  9. n /= 2;
  10. }
  11. for (int i = cnt - 1; i >= 0; i -= 1) {
  12. if (i == cnt - 1) {
  13. cout << "A";
  14. continue;
  15. }
  16. if (a[i] == 1)cout << "BA";
  17. else cout << "B";
  18. }
  19. }

D - Pair of Balls

赛时懵逼了,一下子没想到用 map 去处理

题意:

  • AtCoder Beginner Contest 216 - 图30 个球,编号都在 AtCoder Beginner Contest 216 - 图31AtCoder Beginner Contest 216 - 图32 的范围内,每个编号的球恰好有两个,放入 AtCoder Beginner Contest 216 - 图33 个容器中,每个容器大小为 AtCoder Beginner Contest 216 - 图34 ,现在有一种操作:从某个容器顶部的球(前提是另外一个容器的顶部也是这个球的编号),然后把这两个球都去掉,重复操作下来,问能否把全部栈清空。

思路:
数组 AtCoder Beginner Contest 216 - 图35 代表编号为 AtCoder Beginner Contest 216 - 图36的球在哪个容器中,对每一个容器 AtCoder Beginner Contest 216 - 图37 顶部依次搜索,如果另一个容器 AtCoder Beginner Contest 216 - 图38 顶部跟当前容器顶部相同就去掉,然后再对容器 AtCoder Beginner Contest 216 - 图39 搜索,具体看代码。

  1. const int N = 2e5 + 10;
  2. queue<int>q[N];
  3. int mp[N];
  4. void dfs(int i) {
  5. int u = mp[q[i].front()];
  6. q[u].pop();
  7. q[i].pop();
  8. while (!q[u].empty() and mp[q[u].front()]) dfs(u);
  9. if (!q[u].empty()) mp[q[u].front()] = u;
  10. }
  11. int main() {
  12. cin.tie(nullptr)->sync_with_stdio(false);
  13. int n, m;
  14. cin >> n >> m;
  15. for (int i = 1, k; i <= m; ++i) {
  16. cin >> k;
  17. for (int j = 1, x; j <= k; ++j) {
  18. cin >> x;
  19. q[i].push(x);
  20. }
  21. }
  22. for (int i = 1; i <= m; ++i) {
  23. while (!q[i].empty() and mp[q[i].front()]) dfs(i);
  24. if (!q[i].empty()) mp[q[i].front()] = i;
  25. }
  26. bool f = 0;
  27. for (int i = 1; i <= m; ++i) {
  28. if (!q[i].empty()) {f = 1; break;}
  29. }
  30. cout << (!f ? "Yes\n" : "No\n");
  31. }

E - Amusement Park

题意:

AtCoder Beginner Contest 216 - 图40 来到了一个游乐园,游乐园里有 AtCoder Beginner Contest 216 - 图41 个景点,并且第 AtCoder Beginner Contest 216 - 图42 个景点的乐趣最开始是 AtCoder Beginner Contest 216 - 图43 随着 AtCoder Beginner Contest 216 - 图44 的游玩,他的满足感数值会增加当前游玩景点乐趣值,但每一次游玩该景点后此景点乐趣值 AtCoder Beginner Contest 216 - 图45AtCoder Beginner Contest 216 - 图46 最多可以以任何顺序乘坐景点K次。

请问 AtCoder Beginner Contest 216 - 图47 能得到的最大可能的满意度是什么?

AtCoder Beginner Contest 216 - 图48 除了乘坐景点外,没有什么能影响 AtCoder Beginner Contest 216 - 图49 的满意度。

思路:

感觉做过哎(雾)

为了使得满意度最大化,肯定是先游玩乐趣值大的那几个景点,并且判断是不是能重复游玩使得值最大化。

详细见代码

const int N = 2e5 + 10;
ll a[N];
int main() {
    cin.tie(nullptr)->sync_with_stdio(false);
    ll n, k;
    cin >> n >> k;
    for (int i = 1; i <= n; ++i) cin >> a[i];
    sort(a + 1, a + 1 + n, greater<ll>());
    ll ans = 0;
    for (int i = 1; i <= n; ++i) {
        ll t = i * (a[i] - a[i + 1]);
        if (k >= t) k -= t, ans += (a[i] + a[i + 1] + 1) * t / 2;
        else {
            ll tt = k / i, j = k % i;
            ans += (a[i] + a[i] - tt + 1) * tt / 2 * i + j * (a[i] - tt);
            break;
        }
    }
    cout << ans;
}