RC-u1 热҈热҈热҈
分数 10
作者 DAI, Longao
单位 杭州百腾教育科技有限公司
热҈热҈热҈……最近热得打的字都出汗了!
幸好某连锁餐厅开启了气温大于等于 35 度即可获得一杯免费雪碧的活动。但不知为何,在每个星期四的时候,这个活动会暂停一天……
现在给定连续的若干天的气温情况以及给定的第一天是星期几,请你算出有多少天你可以喝到免费的雪碧,又有多少天是因为星期四而导致你喝不到雪碧的。
输入第一行是两个正整数 N, W (1≤N≤50,1≤W≤7),表示给定连续的 N 天,下面给定的第一天是星期 W(7 等于星期天)。
接下来的一行给出 N 个用一个空格隔开的、小于 60 的整数,第 i 个数表示第 i 天的温度。保证温度大于等于 -273 度。
输出两个数,第一个是你能喝到免费雪碧的天数,第二个是你本来能喝到免费雪碧、但因为是星期四而无法喝到的天数。
15 3
33 35 34 36 37 40 32 31 30 29 28 29 33 38 40
5 1
#include
using namespace std;
#define endl '\n'
//#define int long long
using u32 = unsigned;
using i64 = long long;
using u64 = unsigned long long;
using PII = pair;
const int N=1e5+5;
void solve() {
int n,w;
cin >> n>>w;
int t;
int a=0,b=0;
for (int i = 0; i < n; i++)
{
cin>>t;
if(t>=35){
if(w==4){
b++;
}else a++;
}
w++;
if(w==8)w=1;
}
cout<_/___.' >' "".
* | | : `- \`.;`\ _ /`;.`/ - ` : | |
* \ \ `_. \_ __\ /__ _/ .-` / /
* =====`-.____`.___ \_____/___.-`___.-'=====
* `=---='
*
*
* ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
*
* 佛祖保佑 永不宕机 永无BUG
*/
RC-u2 谁进线下了?
分数 15
作者 DAI, Longao
单位 杭州百腾教育科技有限公司
Xepa Legends 是一个第一人称射击类大逃杀(“吃鸡”)游戏,每轮游戏共有 20 支 3 人小队参加,最后获胜的队伍被称为“捍卫者”。
最近 Xepa Legends 举行了亚太地区南赛区的线上比赛,争夺 7 个前往德国曼海姆参加线下赛的资格,国内共有 14 支队伍参与到了其中。因为比赛十分激烈,直到最后谁进了线下仍有巨大的疑问。小 K 喜欢的国内知名战队 DreamTear 因其队内选手杀马特表现不佳,正好卡在出线分数前后,请你赶紧帮帮小 K,计算一下最后的分数情况,看看他喜欢的战队出线了没有吧!
Xepa Legends 的比赛共进行 N 场游戏,在每场游戏中,每支队伍在游戏中会获得一个排名和一个杀敌数(击败其他队伍玩家的数量),一支队伍在一场游戏的得分为杀敌数+排名分,排名分由队伍当场的排名根据以下表格求得:
排名 | 分数 |
---|---|
第一名 | 12 分 |
第二名 | 9 分 |
第三名 | 7 分 |
第四名 | 5 分 |
第五名 | 4 分 |
第六名至第七名 | 3 分 |
第八名至第十名 | 2 分 |
第十一名至第十五名 | 1 分 |
第十六名至第二十名 | 0 分 |
例如,
注:本题与实际情况无关,所有比赛规则、队伍、队员名称均为虚构。
输入第一行是一个正整数 N (≤20),表示有 N 场比赛。
接下来有 N 部分输入,每部分是一场比赛的情况。对每一场比赛,信息共分 20 行,第 i 行(i=1,⋯,20)给出的两个非负整数 p 和 k 表示第 i 支队伍在这场比赛里获得了第 p 名、杀敌数为 k。
数据保证所有给定的情况中,排名永远大于等于 1 且小于等于 20,杀敌数小于等于 57。
输出 20 行,按编号从小到大依次输出队伍的编号及该队全部游戏结束时的总分。
3
6 2
7 3
11 5
10 1
2 9
5 8
14 3
4 3
1 6
18 1
12 1
20 0
13 0
3 2
16 4
8 1
19 0
9 4
17 1
15 0
8 2
19 1
12 2
1 9
10 1
7 5
18 0
14 0
5 2
4 4
2 5
6 2
16 3
13 1
20 0
3 7
9 3
15 0
17 5
11 3
18 0
5 2
2 9
9 4
4 7
10 3
16 0
1 6
20 0
15 1
6 0
3 6
14 3
7 4
19 0
17 0
8 9
11 0
13 5
12 0
1 9
2 13
3 27
4 30
5 33
6 25
7 4
8 27
9 24
10 12
11 19
12 18
13 8
14 18
15 4
16 17
17 16
18 8
19 12
20 6
#include
using namespace std;
#define endl '\n'
//#define int long long
using u32 = unsigned;
using i64 = long long;
using u64 = unsigned long long;
using PII = pair;
const int N=1e5+5;
int rk(int a){
if(a==1)return 12;
if(a==2)return 9;
if(a==3)return 7;
if(a==4)return 5;
if(a==5)return 4;
if(a==6||a==7)return 3;
if(a>=8&&a<=10)return 2;
if(a>=11&&a<=15)return 1;
return 0;
}
void solve() {
int n;
cin >> n;
int p,k;
mapmp;
for (int i = 1; i <= n; i++)
{
for (int j = 1; j <=20; j++)
{
cin>>p>>k;
mp[j]+=rk(p)+k;
}
}
for (auto i :mp)
{
cout<_/___.' >' "".
* | | : `- \`.;`\ _ /`;.`/ - ` : | |
* \ \ `_. \_ __\ /__ _/ .-` / /
* =====`-.____`.___ \_____/___.-`___.-'=====
* `=---='
*
*
* ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
*
* 佛祖保佑 永不宕机 永无BUG
*/
RC-u3 暖炉与水豚
分数 20
作者 DAI, Longao
单位 杭州百腾教育科技有限公司
PapiCon(@PapilloteContet)出了许多有意思的谜题,其中有一道关于水豚的谜题是这样的:
来源:x.com/PapilloteContet
在一个 N×M 的矩阵中有若干水豚以及暖炉,暖炉可以辐射以它自身为中心的 3×3 范围里的水豚,使其变得暖呼呼的。谜题里存在一只冷的要命的水豚,你需要移动其中的一个暖炉,使所有水豚都变得暖呼呼的。
在往下读题前,如果你有兴趣的话,不妨思考一下如何解答这个谜题。(思考结果与题目无关,可跳过。)
这个谜题的关键在于,单纯从图中能看到的暖炉来说是无解的,但如果注意到,第 3 行第 6 列的水豚明明周围没有暖炉,却也处于暖呼呼的状态,就能推测出来图中的那个对话框挡住了一个暖炉,只要移动这个暖炉就可以完成题目的要求。
现在我们将谜题一般化,对于给定的一个 N×M 的矩阵、对应的所有水豚状态、以及能看到的暖炉摆放情况,已知最多只有一只水豚的状态不太对劲(周围没有暖炉却暖呼呼的),你需要推测有哪些格子可能藏了暖炉。一个空格可能藏了暖炉可以理解为:当前空格设置暖炉后整个矩阵的状态会从不合法变为合法。
输入第一行是两个正整数 N, M (1≤N,M≤1000),表示矩阵的大小。
接下来的 N 行,每行有 M 个字符,第 i 行的第 j 个字符表示矩阵中对应位置的状态,其中:
.
表示空格(或者说,看上去是空格的格子);c
表示很冷的水豚;w
表示暖呼呼的水豚;m
表示暖炉。输出若干行,每行两个正整数 r 和 c,表示第 r 行第 c 列有可能藏了一个暖炉,有多个可能时,先按 r 从小到大输出,r 相同时再按 c 从小到大输出。如果没有一个格子可能藏了暖炉, 则在一行中输出Too cold!
。
行与列均从 1 开始编号。
6 8
wm....mw
.w..ww..
..wm.wwm
w.w....w
.m.c.m..
w.....w.
2 7
3 5
4 6
4 7
#include
#include
using namespace std;
int main(){
ios::sync_with_stdio(false);
cin.tie(nullptr);
int N, M;
cin >> N >> M;
vector grid(N);
for(int i = 0; i < N; i++){
cin >> grid[i];
}
// 标记所有可见暖炉的覆盖范围
vector> heated(N, vector(M, false));
// 遍历所有可见暖炉,标记其3×3覆盖范围
for(int i = 0; i < N; i++){
for(int j = 0; j < M; j++){
if(grid[i][j] == 'm'){
for(int di = -1; di <= 1; di++){
for(int dj = -1; dj <= 1; dj++){
int ni = i + di, nj = j + dj;
if(ni >= 0 && ni < N && nj >= 0 && nj < M){
heated[ni][nj] = true;
}
}
}
}
}
}
// 找出异常水豚:'w'但不在heated区域内
int anomaly_r = -1, anomaly_c = -1;
for(int i = 0; i < N; i++){
for(int j = 0; j < M; j++){
if(grid[i][j] == 'w' && !heated[i][j]){
anomaly_r = i;
anomaly_c = j;
break;
}
}
if(anomaly_r != -1) break;
}
// 标记禁区:冷水豚'c'的3×3邻域不能放暖炉
vector> forbidden(N, vector(M, false));
for(int i = 0; i < N; i++){
for(int j = 0; j < M; j++){
if(grid[i][j] == 'c'){
for(int di = -1; di <= 1; di++){
for(int dj = -1; dj <= 1; dj++){
int ni = i + di, nj = j + dj;
if(ni >= 0 && ni < N && nj >= 0 && nj < M){
forbidden[ni][nj] = true;
}
}
}
}
}
}
// 寻找候选位置
vector> candidates;
for(int i = 0; i < N; i++){
for(int j = 0; j < M; j++){
if(grid[i][j] == '.' && !forbidden[i][j]){
if(anomaly_r != -1){
// 必须能覆盖异常水豚(在其3×3邻域内)
if(abs(i - anomaly_r) <= 1 && abs(j - anomaly_c) <= 1){
candidates.push_back({i+1, j+1});
}
} else {
// 没有异常水豚,当前状态已合法
// 按题意应该输出"Too cold!"
}
}
}
}
if(candidates.empty()){
cout << "Too cold!" << endl;
} else {
for(auto &p : candidates){
cout << p.first << " " << p.second << endl;
}
}
return 0;
}
RC-u4 章鱼图的判断
分数 25
作者 DAI, Longao
单位 杭州百腾教育科技有限公司
对于无向图 G=(V,E),我们将有且只有一个环的、大于 2 个顶点的无向连通图称之为章鱼图,因为其形状像是一个环(身体)带着若干个树(触手),故得名。
给定一个无向图,请你判断是不是只有一个章鱼子图存在。
输入第一行是一个正整数 T (1≤T≤5),表示数据的组数。
每组数据的第一行是两个正整数 N,M (1≤N,M≤105),表示给定的无向图有 N 个点,M 条边。
接下来的 M 行,每行给出一条边两个端点的顶点编号。注意:顶点编号从 1 开始,并且题目保证任何边不会重复给出,且没有自环。
对于每组数据,如果给定的图里只有一个章鱼子图,则在一行中输出 Yes
和章鱼子图环的大小(及环中顶点数),其间以 1 个空格分隔。
否则,则在一行中输出 No
和图中章鱼子图的个数,其间以 1 个空格分隔。
3
10 10
1 3
3 5
5 7
7 9
1 2
2 4
2 6
3 8
9 10
1 9
10 10
1 3
3 5
5 7
7 9
9 1
1 2
2 4
4 8
8 10
10 1
10 10
1 3
3 5
5 7
7 9
9 1
2 4
4 8
8 10
10 2
10 6
Yes 5
No 0
No 2
#include
#include
#include
#include
using namespace std;
const int NMAX = 100000;
vector> adj; // 邻接表
// 全局变量用于环检测(只在一个“章鱼图”分量中使用)
int cycleLength; // 检测到的环长
// dfsCycle 在连通分量内对 u 做 DFS,
// 参数 allowed 指示哪些结点属于当前连通分量。
// par 数组记录每个结点的父亲结点。
// localVisited 记录本 DFS 中的访问情况。
// 如果在 DFS 中发现一个后向边,则通过回溯父亲链计算环长并返回 true。
bool dfsCycle(int u, int parent, const vector& allowed, vector& localVisited, vector& par) {
localVisited[u] = true;
par[u] = parent;
for (int v : adj[u]) {
if (!allowed[v]) continue; // 不在当前连通分量内
if (v == parent) continue; // 忽略父亲结点
if (!localVisited[v]) {
if (dfsCycle(v, u, allowed, localVisited, par))
return true;
} else {
// 发现一个后向边:u -> v,其中 v 已访问且 v 不是 u 的父亲
// 利用 par 数组回溯计算环长
int len = 1;
int cur = u;
while(cur != v) {
len++;
cur = par[cur];
}
cycleLength = len;
return true;
}
}
return false;
}
int main(){
ios::sync_with_stdio(false);
cin.tie(nullptr);
int T;
cin >> T;
while (T--) {
int n, m;
cin >> n >> m;
adj.assign(n+1, vector());
for (int i = 0; i < m; i++){
int u, v;
cin >> u >> v;
adj[u].push_back(v);
adj[v].push_back(u);
}
// visited 用于遍历整个图,记录全局是否访问过
vector visited(n+1, false);
int octopusCount = 0;
int answerCycleLength = 0; // 如果只有一个章鱼图,记录其环长
// 遍历所有连通分量
for (int i = 1; i <= n; i++){
if (visited[i]) continue;
// 使用 DFS 获得连通分量中的所有结点
vector compNodes;
// 用简单的栈实现 DFS
vector stack;
stack.push_back(i);
visited[i] = true;
while(!stack.empty()){
int u = stack.back();
stack.pop_back();
compNodes.push_back(u);
for (int v : adj[u]){
if (!visited[v]) {
visited[v] = true;
stack.push_back(v);
}
}
}
// 统计当前连通分量结点数与内部边数(注意边重复计数)
int Vcomp = compNodes.size();
int Ecomp = 0;
for (int u : compNodes) {
Ecomp += adj[u].size();
}
Ecomp /= 2; // 每条边被计数2次
// 如果结点数小于 3 或边数不等于结点数,则不可能为章鱼图
if (Vcomp < 3 || Ecomp != Vcomp) continue;
// 对当前连通分量准备标记(allowed 数组:标记哪些结点属于该分量)
vector allowed(n+1, false);
for (int u : compNodes) {
allowed[u] = true;
}
// 对该分量内重新做 DFS(注意此处需要单独记录访问情况)
vector compVisited(n+1, false);
vector par(n+1, -1);
bool foundCycle = false;
// 任取分量中的第一个结点开始 DFS
for (int u : compNodes) {
if (!compVisited[u]){
if (dfsCycle(u, -1, allowed, compVisited, par)){
foundCycle = true;
break;
}
}
}
// 如果成功检测到唯一环(一定会检测到,因为 Ecomp == Vcomp 证明该分量必定有一个环)
if (foundCycle){
octopusCount++;
// 记录第一个章鱼图的环长
answerCycleLength = cycleLength;
}
}
if (octopusCount == 1)
cout << "Yes " << answerCycleLength << "\n";
else
cout << "No " << octopusCount << "\n";
}
return 0;
}
RC-u5 工作安排
分数 30
作者 DAI, Longao
单位 杭州百腾教育科技有限公司
小 K 有 N 项工作等待完成,第 i 项工作需要花 ti 单位时间,必须在 di 时刻或之前完成,报酬为 pi。假设小 K 工作时刻从 0 开始,且同一时刻只能做一项工作、工作一旦开始则不可中断或切换至其他工作,请你帮小 K 规划一下如何选择合适的工作,使小 K 可以获得最多的报酬。
输入第一行是一个正整数 T (≤5),表示数据的组数。
接下来有 T 组数据,每组数据第一行是一个正整数 N (≤5000),表示待完成工作的数量。接下来的 N 行,每行三个非负整数 ti、di、pi (均 ≤5000;1≤i≤N),表示第 i 项工作需要花费的时间、截止时间以及报酬。
对于每组数据,输出小 K 能获得最多的报酬是多少。
3
5
1 2 50
3 3 100
1 5 1
3 2 5000
4 5 30
5
1 2 50
3 3 20
1 5 1
3 2 5000
4 5 30
5
1 2 50
3 3 100
1 5 1
3 2 5000
5 5 800
101
80
800
#include
#include
#include
using namespace std;
struct Job {
int t, d, p;
};
int main(){
ios::sync_with_stdio(false);
cin.tie(nullptr);
int T;
cin >> T;
while(T--){
int n;
cin >> n;
vector jobs(n);
int maxDeadline = 0;
for (int i = 0; i < n; i++){
cin >> jobs[i].t >> jobs[i].d >> jobs[i].p;
maxDeadline = max(maxDeadline, jobs[i].d);
}
// 按截止时间从小到大排序
sort(jobs.begin(), jobs.end(), [](const Job &a, const Job &b){
return a.d < b.d;
});
// 定义dp数组,容量为maxDeadline+1,dp[j]: 完成总时长为j时能够获得的最大收益
vector dp(maxDeadline + 1, 0);
// 遍历所有任务
for (int i = 0; i < n; i++){
int t = jobs[i].t, d = jobs[i].d, p = jobs[i].p;
// 倒序遍历更新dp,注意 j 必须不超过任务截止时间 d
for (int j = d; j >= t; j--){
dp[j] = max(dp[j], dp[j - t] + p);
}
}
// 答案为所有时间点下的最大收益
int ans = 0;
for (int j = 0; j <= maxDeadline; j++){
ans = max(ans, dp[j]);
}
cout << ans << "\n";
}
return 0;
}