欢迎大家订阅我的专栏:算法题解:C++与Python实现!
本专栏旨在帮助大家从基础到进阶 ,逐步提升编程能力,助力信息学竞赛备战!
专栏特色
1.经典算法练习:根据信息学竞赛大纲,精心挑选经典算法题目,提供清晰的代码实现与详细指导,帮助您夯实算法基础。
2.系统化学习路径:按照算法类别和难度分级,从基础到进阶,循序渐进,帮助您全面提升编程能力与算法思维。
适合人群:
- 准备参加蓝桥杯、GESP、CSP-J、CSP-S等信息学竞赛的学生
- 希望系统学习C++/Python编程的初学者
- 想要提升算法与编程能力的编程爱好者
附上汇总贴:历年CSP-S复赛真题解析 | 汇总
【题目来源】
洛谷:P11231 [CSP-S 2024] 决斗 - 洛谷
【题目描述】
今天是小 Q 的生日,他得到了 n n n 张卡牌作为礼物。这些卡牌属于火爆的“决斗怪兽”,其中,第 i i i 张卡代表一只攻击力为 r i r_i ri,防御力也为 r i r_i ri 的怪兽。
一场游戏分为若干回合。每回合,小 Q 会选择某只怪兽 i i i 以及另一只怪兽 j ( i ≠ j ) j(i\neq j) j(i=j),并让怪兽 i i i 向怪兽 j j j 发起攻击。此时,若怪兽 i i i 的攻击力小于等于怪兽 j j j 的防御力,则无事发生;否则,怪兽 j j j 的防御被打破,怪兽 j j j 退出游戏不再参与到剩下的游戏中。一只怪兽在整场游戏中至多只能发起一次攻击。当未退出游戏的怪兽都已发起过攻击时,游戏结束。
小 Q 希望决定一组攻击顺序,使得在游戏结束时,未退出游戏的怪兽数量尽可能少。
【输入】
输入的第一行包含一个正整数 n n n,表示卡牌的个数。
输入的第二行包含 n n n 个正整数,其中第 i i i 个正整数表示第 i i i 个怪兽的攻击力及防御力 r i r_i ri。
【输出】
输出一行包含一个整数表示游戏结束时未退出游戏的怪兽数量的最小值。
【输入样例】
5
1 2 3 1 2
【输出样例】
2
【算法标签】
《洛谷 P11231 决斗》 #CSP-S提高级# #2024# #O2优化#
【代码详解】
#include <bits/stdc++.h>
using namespace std;
const int N = 100005; // 定义最大敌人数量
int n, r[N]; // n: 敌人数量, r[N]: 存储每个敌人的攻击范围
int main() {
// 输入敌人数量
cin >> n;
// 输入每个敌人的攻击范围
for (int i = 1; i <= n; i++)
cin >> r[i];
// 将敌人的攻击范围从小到大排序
sort(r + 1, r + n + 1);
// 初始化答案为敌人总数(最坏情况)
int ans = n;
// 使用双指针法计算最小未被消灭的敌人数量
for (int i = 1, j = 2; i <= n; i++)
{
// 跳过所有攻击范围相同的敌人
while (j <= n && r[j] == r[i])
j++;
// 如果找到攻击范围更大的敌人
if (j <= n && r[j] > r[i])
{
j++; // 移动右指针
ans--; // 可以消灭一个敌人,总数减1
}
}
// 输出最终未被消灭的敌人最小数量
cout << ans << endl;
return 0;
}
【运行结果】
5
1 2 3 1 2
2