题解:P12396 「FAOI-R9」平民上篮

Firsry AC/WA/RE/TLE

幸好中考体考选的是排球……

思路

这个题耐心的分类讨论即可,如下:

  • 在已有的操作序列当中,需要统计的有:

    1. 已经花掉的时间;
    2. 已经完成的组数;
    3. 每个时间的状态,便于处理下一个状态或者补充新的操作序列。

    其中状态可以分为是否在篮下,是否投进,失败了几次

    注意在新的一轮 G 的时候对于是否投进以及失败次数进行重置;
    判定是否完成一组的时候是在 B 的同时检查是否投进以及失败次数。

  • 在补充新的序列的时候,考虑两个阶段:

    1. 上一组没有完成的部分,此时会在篮下,进行分类讨论:

      1. 对于已经完成了 组、已经投进和已经失败不少于三次的情况,我们并不需要讨论新的投篮,可以直接回来;
      2. 否则,我们考虑一次投进以及补充剩下失败次数哪个花费更短;

      一番操作之后,总组数增加一,容易看出这么做,对于不足四个组的合理,对于不少于四个组的也没有影响。

    2. 对于新开的几个组,考虑需要多少个组(不会少于零个),以及每个组选择投进还是失败三次,相乘再与答案相加即可。

杂言

GBAW, 个人认为对应是 Go,Back,AC,WA,所以变量名直接一通乱搞。

代码

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
#include<bits/stdc++.h>
#define ll long long

using namespace std;

ll a, b, c;
string s;

ll ans = 0;
ll setCount = 0;
ll WACount = 0;
bool isUnderBasket = false;
bool isAC = false;

int main() {
scanf("%lld%lld%lld", &a, &b, &c);
cin >> s;
for (char ch : s) {
if (ch == 'G') {
ans += a;
isUnderBasket = true;
WACount = 0;
isAC = false;
} else if (ch == 'W')
ans += c, WACount++;
else if (ch == 'A')
ans += b, isAC = true;
else if (ch == 'B') {
ans += a;
isUnderBasket = false;
if (isAC || WACount >= 3)
setCount++;
}
}
if (isUnderBasket) {
if (setCount < 4 && !(isAC || WACount >= 3)) {
ll timeAC = b;
ll timeWA = (3 - WACount) * c;
ans += min(timeAC, timeWA);
}
ans += a;
isUnderBasket = false;
setCount++;
}
ll setNeed = max(0LL, 4 - setCount);
ll setTime = min(2 * a + b, 2 * a + 3 * c);
ans += setNeed * setTime;
cout << ans;
return 0;
}
  • Title: 题解:P12396 「FAOI-R9」平民上篮
  • Author: Firsry
  • Created at : 2025-08-10 08:20:48
  • Updated at : 2025-08-10 09:22:47
  • Link: https://firsryfan.github.io/2025/08/10/题解:P12396-「FAOI-R9」平民上篮/
  • License: This work is licensed under CC BY-NC-SA 4.0.
On this page
题解:P12396 「FAOI-R9」平民上篮