【题解】CF6 合集
前言:
- 本人不会 LaTeX……请见谅
- 码风奇特,不喜勿喷哈
- 题面翻译取自 luogu,本蒟蒻也会安置原题链接
- 保证文章中不出现“显然”或者“注意到”,可能会出现“易证”
- AC 代码会放置在每一个题目的最底端,为防止 ban 码的情况出现,不设置跳转链接
- 有写错的地方欢迎各位神犇指正
- 本套题共 5 道,鉴于前几题可以直接做,预计阅读 + 理解时间小于 40min
正片开始!
CF6A
题面(可从下方链接跳转看原题题面):
给定 4 根木棍的长度,如果它们中存在 3 根木棍可以组成三角形,输出 TRIANGLE
;如果它们无法组成三角形,但是它们中存在 3 根木棍可以组成退化的三角形(任意两边之和大于等于第三边,但是不是三角形),输出 SEGMENT
;否则,输出 IMPOSSIBLE
注意: 木棍不能折断,也不能只用一部分长度
序言 & 结论:
n≤4,怎么做都行……
难度:红题(建议直接水过)
推理过程:
- 排序,直接枚举所有可能方案,并判断
- 容斥也可行(杀鸡焉用牛刀?)
细节处理:
- 退化的三角形……
- 没排序 qwq
代码:
水题速切
点击查看代码
#include<iostream>
#include<cstdio>
#include<algorithm>
using namespace std;
int a[4],b[3],op;
void dfs(int cnt,int pos){
if(cnt==3){
if(b[0]+b[1]>b[2]){
op=2;
}
if(b[0]+b[1]==b[2]&&!op){
op=1;
}
}else{
for(int i=pos;i<4;i++){
b[cnt]=a[i];
dfs(cnt+1,i+1);
}
}
return;
}
int main(){
for(int i=0;i<4;i++){
scanf("%d",&a[i]);
}
sort(a,a+4);
dfs(0,0);
if(op==0){
printf("IMPOSSIBLE\n");
}
if(op==1){
printf("SEGMENT\n");
}
if(op==2){
printf("TRIANGLE\n");
}
return 0;
}
----------------------------云落的分割线
----------------------------
CF6B
题面(可从下方链接跳转看原题题面):
鉴于 luogu 翻译的不可读,此题不展示中文体面,抱歉!
序言 & 结论:
不是?
学过 bfs 的应该能瞬秒这个题
大型纪录片之《方向数组的来源》
难度:橙题
推理过程:
- n,m≤100,直接枚举每个格子
- 只要搜索到老板的办公桌,直接四个方向判断
- 若是字母且不是老板自己的办公桌,就插入一个 set
- set 的使用可以帮我们简化去重的部分
细节处理:
- 不要用 scanf 输入字符矩阵
- 四方向判断的时候注意是否在矩阵内(inbound)
- 方向数组不要串
代码:
直接做《》——(自行脑补)
点击查看代码
#include<iostream>
#include<set>
using namespace std;
const int maxn=128;
const int dx[]={1,0,-1,0},dy[]={0,-1,0,1};
int n,m;
char c,mp[maxn][maxn];
set<char> s;
inline bool inbound(int x,int y){
return x>=0&&x<n&&y>=0&&y<m;
}
int main(){
cin>>n>>m>>c;
for(int i=0;i<n;i++){
for(int j=0;j<m;j++){
cin>>mp[i][j];
}
}
for(int i=0;i<n;i++){
for(int j=0;j<m;j++){
for(int k=0;k<4;k++){
if(mp[i][j]==c){
int x=i+dx[k],y=j+dy[k];
if(inbound(x,y)&&mp[x][y]!='.'&&mp[x][y]!=c){
s.insert(mp[x][y]);
}
}
}
}
}
cout<<s.size()<<endl;
return 0;
}
----------------------------云落的分割线
----------------------------
CF6C
题面(可从下方链接跳转看原题题面):
n 个糖,a 从前往后吃,b 从后往前吃,每个糖都有吃完需要的时间,每个人在同一时间只能吃一个,吃完某一个后,才能吃下一个,如果两个人同时开始吃同一个,b 会让给 a,问最后每个人总共吃了多少糖
序言 & 结论:
对于 chocolate 的翻译如它的译文——“糖”
难度:橙题
差点刷新我的最快切题记录
无压行,共计 21 行,如何呢?
推理过程:
- 两句话秒了(算上这句)
- 维护指针,直接模拟,不断更新
细节处理:
代码:
云追不上雨,我追不上她
点击查看代码
#include<iostream>
#include<cstdio>
using namespace std;
const int maxn=1e5+10;
int n,a[maxn];
int main(){
scanf("%d",&n);
for(int i=1;i<=n;i++){
scanf("%d",&a[i]);
}
int pos1=1,pos2=n,sum1=0,sum2=0;
while(pos1<=pos2){
if(sum1<=sum2){
sum1+=a[pos1++];
}else{
sum2+=a[pos2--];
}
}
printf("%d %d\n",pos1-1,n-pos2);
return 0;
}
----------------------------云落的分割线
----------------------------
CF6D
题面(可从下方链接跳转看原题题面):
有一队人,第 i 个人的血量为 hi,你可以用火球点某个人,会对当前的人造成 a 点伤害,对旁边的人造成 b 点伤害
火球不能打 1 号和 n 号,求最少多少发火球烧死所有人
序言 & 结论:
题目终于不水了呢!
难度:绿题
可是范围很小,n≤10
推理过程:
- dp 让我很暴戾,所以我打了个 dfs
- 最简单的 dfs,形如:dfs(x) 表示对 x 号造成伤害……
- 没 ~ 有 ~ 任 ~ 何 ~ 前 ~ 途 ~
- 诶?突然发现——
- 如果增加一个维度,即 dfs(x,k),表示对 x 号造成 k 次伤害……
- 大大优化了时间复杂度,交一发……TLE
- 考虑每次我们判断边界的时候都会遍历整个数组(效率非常低下)
注意到造成伤害的时候?只与左右相关!- 即第 i 个人最多会连带受到第 i−1,i,i+1 三个人的伤害,之后就跟他没有关系了,所以我们到第 i+1 人的时候判断第 i 人是否死亡了,这样就能保证每个人最终都符合要求
- 加入最优性剪枝
细节处理:
- 最后到边界的时候要判断第 n−1 和 第 n 个人是否符合要求
- 回溯!一定要把更新过的全部回溯!
- 剪枝之后要写 return(本蒟蒻神秘的挂分方式)
代码:
码量不大,建议手敲,反对 ban 码
点击查看代码
#include<iostream>
using namespace std;
const int maxn=16,maxl=150+10;
int n,a,b,h[maxn];
int step[maxl],c[maxl],ans=2147483647;
inline void dfs(int k,int p){
if(p>=ans){
return;
}
if(k>=n){
if(h[k]>=0||h[n]>=0){
return;
}
ans=p;
for(int i=1;i<=p;i++){
step[i]=c[i];
}
return;
}
for(int i=0;i<=max(h[k]/a+1,max(h[k-1]/b+1,h[k+1]/b+1));i++){
if(h[k-1]-i*b>=0){
continue;
}
h[k]-=i*a;
h[k-1]-=i*b;
h[k+1]-=i*b;
for(int j=p+1;j<=p+i+1;j++){
c[j]=k;
}
dfs(k+1,p+i);
h[k]+=i*a;
h[k-1]+=i*b;
h[k+1]+=i*b;
}
return;
}
int main(){
scanf("%d%d%d",&n,&a,&b);
for(int i=1;i<=n;i++){
scanf("%d",&h[i]);
}
dfs(2,0);
printf("%d\n",ans);
for(int i=1;i<=ans;i++){
printf("%d ",step[i]);
}
return 0;
}
----------------------------云落的分割线
----------------------------
CF6E
题面(可从下方链接跳转看原题题面):
序言 & 结论:
相信各位已经被前面的水题恶心的不要不要的了
来一发蓝题助助兴
先捧一句:STL 大法好!
推理过程:
- 插入一个桶啊
- 维护小区间呀
- 滑动窗口牛啊
- 不合法就删呀
- 队列往里塞啊
- 输出不要错呀
- 为
1
要特判啊 - STL 大法好呀
细节处理:
- *s.rbegin() - *s.begin() > k,这是一个悲伤的故事
- 论 #include < multiset >
代码:
备花备花!
点击查看代码
#include<iostream>
#include<cstdio>
#include<queue>
#include<set>
using namespace std;
const int maxn=1e5+10;
int n,k,a[maxn],ans;
queue<int> q;
multiset<int> s;
int main(){
scanf("%d%d",&n,&k);
for(int i=1;i<=n;i++){
scanf("%d",&a[i]);
}
if(n==1){
printf("%d %d\n%d %d\n",1,1,1,1);
return 0;
}
int len=1;
s.insert(a[1]);
for(int i=2;i<=n;i++){
s.insert(a[i]);
while(i-len+1>=2&&*s.rbegin()-*s.begin()>k&&len<i){
s.erase(s.find(a[len]));
len++;
}
if(i-len+1==ans){
q.push(i);
}
if(i-len+1>ans){
ans=i-len+1;
while(!q.empty()){
q.pop();
}
q.push(i);
}
}
if(ans!=1){
printf("%d %d\n",ans,q.size());
}else{
printf("%d %d\n%d %d\n",ans,n,1,1);
}
while(!q.empty()){
printf("%d %d\n",q.front()-ans+1,q.front());
q.pop();
}
return 0;
}
完结撒花!
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· winform 绘制太阳,地球,月球 运作规律
· TypeScript + Deepseek 打造卜卦网站:技术与玄学的结合
· AI 智能体引爆开源社区「GitHub 热点速览」
· Manus的开源复刻OpenManus初探
· 写一个简单的SQL生成工具