CSP-S2025 题目解析

news/2025/11/2 22:02:50/文章来源:https://www.cnblogs.com/high-sky/p/19185517

看了我的游记的都知道我每道题目的做题情况。

T1

比较简单的签到题目。

你先贪心选每个数最大的那个组,然后判断有没有某一个组的大于 \(\frac{n}{2}\),显然这种组有且仅有一个。

我们考虑把这个组的某些数换组,那么到 \(frac{n}{2}\) 就够了。

显然换到那个数的第二大的那个组即可,相减一下就是代价,直接用大根堆维护即可。

时间复杂度 \(\mathcal{O}(Tn\log n)\)

#include <iostream>
#include <cstdio>
#include <cstring>
#include <stdlib.h>
#include <algorithm>
#include <vector>
#include <queue>
#define int long long
#define N 100005
using namespace std;
priority_queue<int> q[5];
int n;
struct node{int val,id;
}a[N][5];
signed main(){int T;cin >> T;for (;T--;) {for (int j = 1;j <= 3;j ++) {while(!q[j].empty()) q[j].pop();}scanf("%lld",&n);for (int i = 1;i <= n;i ++)for (int j = 1;j <= 3;j ++) scanf("%lld",&a[i][j].val),a[i][j].id = j;int ans = 0;for (int i = 1;i <= n;i ++) {stable_sort(a[i] + 1,a[i] + 1 + 3,[](node x,node y) {return x.val > y.val;});ans += a[i][1].val;q[a[i][1].id].push(a[i][2].val - a[i][1].val);}// cout << ans << '\n';bool flag = 0;for (int i = 1;i <= 3;i ++)flag |= (q[i].size() > n / 2);if (!flag) {printf("%lld\n",ans);continue;}int mxid = 1;for (int i = 2;i <= 3;i ++)if (q[i].size() > n / 2) {mxid = i;break;}// cout << mxid << '\n';while(q[mxid].size() > n / 2) {int t = q[mxid].top();ans += t;q[mxid].pop();}printf("%lld\n",ans);}system("pause");return 0;
}

T2

并未做出来,原因:误认为 \(2^k\leq 1.5\times 10^6\),就是 \(2^{20}\) 的那个上限,然后就不会了。

但其实显然 \(m\) 是诈骗,压成 \(n-1\) 条边就行了,于是可以得到本题性价比极高的 \(80pts\) 做法:\(\mathcal{O}(2^k(nk)\log (nk))\),感觉 \(CCF\) 现在换成 \(\text{Cure Ultra9}\) 可能能过。

然后你把排序换到外面去就能通过本题了。

再说一说我考场上的思路为什么错:每个城镇贡献一个完全图,这样的连边方式是错误的,因为会多算很多次 \(c\)(但是只没有通过一个大样例就很奇妙)。

T3

赛场上应该是可以切掉的,但是由于 \(T_2\) 没有通过大样例的心理施压导致没有把心思放到这上面来。

CCF 的题面提示我们可以将一个替换操作和被替换询问变成:前缀相同+第一个字符串不同的+第二个字符串不同的+后缀相同的,中间用空格隔开。

我们关心的只是不同的情况,对于前缀和后缀我们只需要判断是不是当前询问的前缀相同的后缀且是其后缀相同的前缀(可能有一点绕,请细细品位),然后肯定可以用 trie树 或者 AC自动机 维护,但是我想先验证一下,打了一个hash。

打了很久,这是交在洛谷只有 \(10pts\) 的赛场复刻代码,不忍直视:

#include <iostream>
#include <cstdio>
#include <cstring>
#include <stdlib.h>
#include <algorithm>
#include <vector>
#include <map>
#define int long long
#define uint unsigned long long
#define N 200005
#define M 5500005
#define PII pair<int,int>
using namespace std;
int n,q;
uint Pow[M],seed = 231;
map<uint,int> mp;
map<uint,vector<PII> >mp2;
signed main(){Pow[0] = 1;for (int i = 1;i < M;i ++) Pow[i] = Pow[i - 1] * seed;cin >> n >> q;for (int i = 1;i <= n;i ++) {string s1,s2;cin >> s1 >> s2;int st = 0;while(s1[st] == s2[st]) st ++;int ed = s1.size() - 1;while(s1[ed] == s2[ed]) ed --;uint h = 0,hh = 0;for (int i = 0;i < st;i ++) h = h * seed + s1[i];h = h * seed + ' ';for (int i = st;i <= ed;i ++) h = h * seed + s1[i],hh = hh * seed + s1[i];h = h * seed + ' ';hh = hh * seed + ' ';for (int i = st;i <= ed;i ++) h = h * seed + s2[i],hh = hh * seed + s2[i];h = h * seed + ' ';for (int i = ed + 1;i < s1.size();i ++) h = h * seed + s1[i];mp[h] ++;mp2[hh].push_back({st,(int)s1.size() - ed - 1});// cout << h << ' ' << hh << '\n';}for (string t1,t2;q --;) {cin >> t1 >> t2;if (t1.size() != t2.size()) {puts("0");continue;}int st = 0;while(t1[st] == t2[st]) st ++;int ed = t1.size() - 1;while(t1[ed] == t2[ed]) ed --;string s = "";for (int i = 0;i < st;i ++) s += t1[i];s += " ";uint h2 = 0;for (int i = st;i <= ed;i ++) s += t1[i],h2 = h2 * seed + t1[i];s += " ";h2 = h2 * seed + ' ';for (int i = st;i <= ed;i ++) s += t2[i],h2 = h2 * seed + t2[i];s += " ";for (int i = ed + 1;i < t1.size();i ++) s += t1[i];vector<uint> hh;uint h = 0;for (auto i : s) h = h * seed + i,hh.push_back(h);int ans = 0;for (auto i : mp2[h2]) {int l = st - i.first,r = st + (2 * (ed - st + 2)) + i.second;// cout << i.first << '-' << i.second << '\n';if (l < 0 || r > s.size()) continue;// cout << l << ' ' << r << '\n';uint hsh = 0;// for (int j = l;j <= r;j ++) hsh = hsh * seed + s[j];if (l == 0) hsh = hh[r];else hsh = hh[r] - hh[l - 1] * Pow[r - l + 1];// cout << hsh << '\n';ans += mp[hsh];}printf("%lld\n",ans);}// system("pause");return 0;
}

样例 \(3\) 是通过不了的,输出的比他多。

你看出来是哪里多了吗?

没错!

由于每一对长度可能相同,但是方案只有这种类型的串的个数,因此我们去重一下就行了,就变成了:

#include <iostream>
#include <cstdio>
#include <cstring>
#include <stdlib.h>
#include <algorithm>
#include <vector>
#include <map>
#define int long long
#define uint unsigned long long
#define N 200005
#define M 5500005
#define PII pair<int,int>
using namespace std;
int n,q;
uint Pow[M],seed = 231;
map<uint,int> mp;
map<uint,vector<PII> >mp2;
signed main(){Pow[0] = 1;for (int i = 1;i < M;i ++) Pow[i] = Pow[i - 1] * seed;cin >> n >> q;for (int i = 1;i <= n;i ++) {string s1,s2;cin >> s1 >> s2;int st = 0;while(s1[st] == s2[st]) st ++;int ed = s1.size() - 1;while(s1[ed] == s2[ed]) ed --;uint h = 0,hh = 0;for (int i = 0;i < st;i ++) h = h * seed + s1[i];h = h * seed + ' ';for (int i = st;i <= ed;i ++) h = h * seed + s1[i],hh = hh * seed + s1[i];h = h * seed + ' ';hh = hh * seed + ' ';for (int i = st;i <= ed;i ++) h = h * seed + s2[i],hh = hh * seed + s2[i];h = h * seed + ' ';for (int i = ed + 1;i < s1.size();i ++) h = h * seed + s1[i];mp[h] ++;mp2[hh].push_back({st,(int)s1.size() - ed - 1});// cout << h << ' ' << hh << '\n';}for (auto i : mp2) {//多了这一段代码sort(i.second.begin(),i.second.end());i.second.erase(unique(i.second.begin(),i.second.end()),i.second.end());mp2[i.first] = i.second;//注意这个,赛场没有写这个所以没有减枝优化}for (string t1,t2;q --;) {cin >> t1 >> t2;if (t1.size() != t2.size()) {puts("0");continue;}int st = 0;while(t1[st] == t2[st]) st ++;int ed = t1.size() - 1;while(t1[ed] == t2[ed]) ed --;string s = "";for (int i = 0;i < st;i ++) s += t1[i];s += " ";uint h2 = 0;for (int i = st;i <= ed;i ++) s += t1[i],h2 = h2 * seed + t1[i];s += " ";h2 = h2 * seed + ' ';for (int i = st;i <= ed;i ++) s += t2[i],h2 = h2 * seed + t2[i];s += " ";for (int i = ed + 1;i < t1.size();i ++) s += t1[i];vector<uint> hh;uint h = 0;for (auto i : s) h = h * seed + i,hh.push_back(h);int ans = 0;for (auto i : mp2[h2]) {int l = st - i.first,r = st + (2 * (ed - st + 2)) + i.second;if (l < 0) break;//排序后的减枝// cout << i.first << '-' << i.second << '\n';if (l < 0 || r >= s.size()) continue;// cout << l << ' ' << r << '\n';uint hsh = 0;// for (int j = l;j <= r;j ++) hsh = hsh * seed + s[j];if (l == 0) hsh = hh[r];else hsh = hh[r] - hh[l - 1] * Pow[r - l + 1];// cout << hsh << '\n';ans += mp[hsh];}printf("%lld\n",ans);}// system("pause");return 0;
}

感觉这个要卡还是能卡的(要卡常),不过在随机数据下面是比较好的,如果刻意去卡的话就是构造一个类似:

 b c 
? b c ?
?? b c ??
....

询问就是都询问 \(b\) 换成 \(c\) 的方案嘛,由于我们注意到其替换方案的字符串总和 \(\leq 5\times 10^6\),而上面那个是等差数列求和,而且绝对不满 \(\sqrt\sum\),差不多是 \(\mathcal{O}(\sum|s_i|+\sum|t_i|+q\sqrt{\sum|s_i|})\)

比较极限,但是应该可以过。

T4

目前不会。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/953831.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

[Record] CSP-S 2025 邮寄

也不算特别寄,但是出考场之后 \(\texttt{T3}\) \(\texttt{T4}\) 都胡出来了,就很难绷。\(\texttt{T1}\) 水题,读完题写写就过了。 \(\texttt{T2}\) 胡思乱想了一会,然而并没有想到比 \(O(m\log m+nk2^k\alpha(n))\…

CH59x/CH58X蓝牙从机白名单使用

蓝牙从机设置白名单,可以只扫描应答(白名单中列出的)设备,只允许(白名单中列出的)设备连接。 蓝牙主机设置白名单,可以只扫描、连接特定的蓝牙设备(白名单中列出的)。 一.蓝牙从机白名单设置有关的函数介绍:…

算法实践第二次作业

一、找第 k 小的数的分治算法描述(伪代码 + 自然语言) 伪代码 plaintext function findKthSmallest(arr, low, high, k): if low == high: # 子数组仅1个元素,直接返回 return arr[low] # 步骤1:选基准元素(此处…

CSP2025总结

J组: 应该是最有机会 AK 的一次。 T1,T2 都是一眼题,用 30min 简单写完后看 T3

hello!

第一篇!第一篇博客园博客! 之前用Astro搭建了个人博客,但是没有评论区的反馈确实博客就像写学习笔记一样,中间出现了很多错误也没人说。。所以来博客园了! 希望这里能见证自己剩下两年半xcpc的学习时光o( ̄▽ ̄)ブ…

docker 交付方案AI设计备份

基于当前项目结构,Docker 交付和在线升级计划如下: Docker 交付与在线升级方案 一、总体架构设计 1.1 容器化策略应用镜像:为 FastAPI 主应用构建独立 Docker 镜像服务编排:使用 Docker Compose 编排所有服务数据持…

2025 CSP-S 游记

Day 0: 大巴上基本啥也没干,发会呆,看会b站就到了。 带了笔记本,晚上CS启动!打了两把小镇一把没赢。/ll 22:30算早睡吗。 Day 1: 上午6:14突然醒了,上了个厕所又睡下去了,7:30再次醒来,感觉睡得比去年好。 因为…

[题解]CSP-S 2025 T1~T3 题解

T1. P14361 [CSP-S 2025] 社团招新 / club Tag:贪心、排序。 因为要求每个社团不超过 \(\dfrac{n}{2}\) 个人,所以无论怎么分配,最多只会有一个社团超出限制。 因此,我们先让每个人选最满意的社团。若存在超出限制…

关于git关联github问题

本地GIT绑定GITHUB 配置本地GIT信息 #配置用户名 git config --global user.name "test"#配置邮箱 git config --global user.email abc@163.com生成本地密钥和公钥 生成ssh文件夹(生成ssh秘钥)(输入$ s…

AT ABC285E Work or Rest 题解

SolutionLink 有趣的 DP 题,难点在于从哪里开始入手以及优化(也许)。 显然 DP 可以方便地处理这个 \(\max\) 值的转移,但是从哪个位置开始 DP 呢?注意到周期呈现环状,也就是说一周的第 \(n\) 天和下一周的第 \(1…

代码复杂度的代价远比你想象得大

引言:复杂度的代价远比你想象得大 在 Java 后端系统演进过程中,代码复杂度是影响可维护性、稳定性和迭代效率的核心因素。然而,复杂度往往被忽视,直到一次“小改动”引发线上事故,才被重新审视。 本文以“复杂度战…

CSP2025 - S 年度总结大会报告

各大 oj 估分:洛谷:\(100+52+10+8=170\)。 小图灵:\(100+60+?+8=168+?\),当时他 \(T_3\) 数据还没有造。 梦熊:\(100+92+30+8=230\),感觉不准。自己估分:\(100+[48,70]+[0,40]+8=[156,218]\)。 第一:明确自己…

25CSP退役游记(11.1更新)

关于我在考虑要不要把S1的P话也加进来这件事 day—— -5 今天天气晴朗,不很像秋天,更不像济南今年的秋天。 考前焦虑期也是要休息的。它从一周之前来,从三四天之后来,这么算三个周能休七八天,比我的假期多多了。但…

第二章实践作业

第二章实践作业分治法找第 k 小的数:基础理解与思考 一、用分治法找第 k 小的数 找第 k 小的数,用分治法来解决其实思路还挺直观的。大概可以分成这几步: 先选一个 “基准数”,随便从数组里挑一个就行,比如选第一…

(补11月)代码大全阅读笔记2

第6-9章的架构设计内容,彻底解答了我长期以来的核心困惑:为何同样实现了基础功能的代码,有的在后续迭代中能轻松响应需求变化,有的却如同“牵一发而动全身”的乱麻,修改一个小功能就引发连锁bug。书中系统阐述的“…

java 基础语法一

java 基础语法一 一、基本概念 冯诺依曼结构,Java三大版本、编译型和解释型语言 1、五大组成部分:运算器、控制器、存储器、输入设备和输出设备;核心特点:采用二进制表示、存储程序原理、顺序执行指令 2、javaSE(…

VisualStudio 2022如何打开.slnx文件格式的解决方案

打开VisualStudio 2022,菜单中设置-选项-环境 > 预览功能 > 勾选最下方的“使用解决方案文件持久性模型”设置,再手动对.slnx文件进行关联设置即可。

(补11月)代码大全阅读笔记3

研读第23-25章关于测试与调试的内容后,我彻底摒弃了“开发负责写代码,测试负责找bug”的错误认知,建立起“开发者是质量第一责任人”的核心意识。书中一组数据让我尤为震撼:单元测试阶段发现并修复bug的成本,仅为…

CSP2025 - S 游记

Day -14 那天的模拟赛考得不错,拿了全校第二。 Day -13 太阳神开家长会骂了我们竞赛生。 心情不爽。 Day -11 晚上上厕所偶遇 xz,xz说我状态不错继续保持。 心情大好。 Day -7 集训,但是状态明显降低。 Day -5 没有…

CSP-S游记

CSP-S游记 首先读题,T1感觉直接贪心即可,T2应该不难,T3没想法,T4是计数我比较喜欢。 T1很快想出来代码也很好写20分钟过掉。 T2很容易想到 \(O(2^kn\log n)\) 的做法,但不确定能不能过就想优化把log去掉,想了一个…