AtCoder Grand Contest 055 题解
A
赛时直到最后 10min 才做出这个 A 题,之前猜了一个结论一直没敢写,本来不抱啥希望 AC 的结果比赛结束时交了一发竟然 A 了,由此可见我的水平之菜/dk
考虑每次取出字符串开头字符,不妨设之为 \(c_1\),以及字符串末尾的最靠后的不同于 \(c_1\) 的字符,不妨设之为 \(c_2\),设除了 \(c_1,c_2\) 之外另一个字符为 \(c_3\),我们就维护两个指针 \(l,r\),以及一个变量 \(cnt\) 表示目前跳了多少步,我们每次贪心地找到 \(l\) 后面下一个 \(c_1\),以及 \(r\) 前一个 \(c_2\),然后分别令 \(l,r\) 为这两个位置,并令 \(cnt\) 加一,如此操作下去直到 \((l,r)\) 中 \(c_3\) 个数 \(<cnt\) 即可,然后令这些元素组成一个子序列并将这些元素从序列中删去。
然鹅一个我不太能理解的地方是,为什么这样最少 6 个子序列就能划分整个字符串 \(S\),赛时的想法是可能与每组 \((c_1,c_2,c_3)\) 最多出现一次有关,但是这个结论显然是错误的,并且貌似官方题解也并没有采用上文所述的做法。有哪位好心的鸽鸽能给个证明,或者能给组 hack 数据把上面的做法叉掉啊/kel
B
赛时没有想出来,甚至连最起码的思路也没有,说明我还是不太适合做这样的思维题啊/kk
考虑将 \(S\) 第一个位置上的字符加 \(2\)(即,A 变成 C,B 变成 A,C 变成 B),第二个位置上的字符加 \(1\),第三个位置上的字符加 \(0\),第四个位置上的字符加 \(2\),第五个位置上的字符加 \(1\),以此类推,那么不难发现,每次操作等价于将一段长度为 \(3\) 的,且三个字符完全相同的连续段全部变成任意一种字符,那么我们考虑这样的过程:我们从左往右遍历 \(S\) 的每一个字符,并维护一个栈存储当前没有被消除完毕的字符,每次往栈顶加入当前遍历到的字符,如果栈顶三个字符全部相同则将这三个字符直接弹出栈,那么可以发现,我们弹出栈的那些字符是可以自由搭配成连续段插入序列的任何一个位置的,而我们没有弹出栈,也就是栈中剩下的那些字符——它们的相对顺序是不会发生变化的,因此我们考虑对 \(S,T\) 都执行一遍上面的操作,然后检验 \(S,T\) 匹配完以后栈中的元素是否相同即可。
时间复杂度 \(\Theta(n)\)。
C
一道挺有意思的数数题,赛时 115min 刚出来还是挺有成就感的(
首先一个显然的事实是,\(A\) 数组中最多只有两种不同的元素,如果 \(A\) 中有两种不同的元素,那么较大者必然是原序列的 LIS。
特判掉 \(A\) 中只有一种元素的情况,打个表可以发现 \(A\) 中只有一种元素的情况符合条件,当且仅当 \(A\) 中唯一的元素 \(\le\lfloor\dfrac{m}{2}\rfloor\),或者等于 \(n-1\)。
我们假设 \(P\) 中 LIS 的长度为 \(l\),那么不难发现,\(A\) 中等于 \(l-1\) 的位置都是 \(P\) 所有 LIS 的必经之点,因此我们可以将原题面中每个元素都 \(\le m\) 序列计数问题转化为 01 序列计数问题,其中一个位置是 \(1\) 当且仅当它是 LIS 的必经之点,否则表明它不是 LIS 的必经之点。
考虑什么样的 01 序列符合要求,打个表可以发现,一个 01 序列符合要求,当且仅当它 \(1\) 的个数 \(c_1\le l\),并且我们把它所有 \(0\) 的连续段提取出来,设它们的长度为 \(L_1,L_2,L_3,\cdots,L_k\),满足 \(c_1+\sum\limits_{i=1}^k\lfloor\dfrac{L_i}{2}\rfloor\ge l\),比较感性的证明大概就,我们对所有连续的 \(0\) 段的相邻元素两两配对,然后用类似于阶梯状的方式在这些相邻元素上填数,然后对于那些落单的元素就从 \(n\) 开始从大往小填,比如 \(01\) 序列 \(100000100010\) 就对应序列 \([1,3,2,5,4,12,6,8,7,11,10,9]\),不难发现这样可以使原序列的 LIS 达到最大值,如果要求的 LIS 比这还大就办不到了。
因此我们枚举 01 序列中有多少个 \(1\),以及有多少个落单的 \(0\),设它们分别为 \(i,j\),那么显然就有 \(c_1+\sum\limits_{i=1}^k\lfloor\dfrac{L_i}{2}\rfloor=i+\dfrac{n-i-j}{2}\),故 \(l\) 的范围就是 \([\max(i,3),\min(i+\dfrac{n-i-j}{2},m)]\),然后考虑怎样排列这个 01 序列,首先将落单的 0 插入 \(i\) 个 \(1\) 组成的 \(i+1\) 个缝隙的方案数为 \(\dbinom{i+1}{j}\),将剩余 \(\dfrac{n-i-j}{2}\) 组配好对的 \(00\) 插入 \(i+1\) 个空隙的方案数为 \(\dbinom{\dfrac{n-i-j}{2}+i}{i}\),因此 \(A\) 中有两个不同元素的部分的答案可以写成:
\]
看看这个式子,是不是很简单啊(大雾
\(\Theta(n^2)\) 计算即可。
D
一道神仙找性质题。
开始翻译官方题解(bushi
首先抛出结论:如果设 \(M_{AB}\) 为 \(S\) 所有前缀中 B 数量减 A 数量的最大值,\(M_{BC},M_{CA}\) 同理,那么一个序列 \(S\) 符合条件,当且仅当 \(M_{AB}+M_{BC}+M_{CA}\le n\)。
必要性:我们记 ABC,BCA,CAB 的数量分别为 \(A,B,C\),那么我们发现,当我们放入一个 ABC 或 CAB,只会导致某些前缀的 B 数量减去 A 数量减少,只有我们放入 BCA 时才会使该值增加,因此 \(M_{AB}\le B\),同理 \(M_{BC}\le C,M_{CA}\le A\),三者加起来可得到 \(M_{AB}+M_{BC}+M_{CA}\le n\)。
充分性:我们考虑求出第 \(i\) 个 A,B,C 所在的位置(\(i\in[1,n]\)),那么我们这样构造:第 \(i\) 个 A 匹配第 \(i+M_{AB}\) 个 B 以及第 \(i+M_{AB}+M_{BC}\) 个 C(如果超过了 \(n\) 则自动减去 \(n\),即第 \(i+n\) 个 X 即为第 \(i\) 个 X,\(X\in\{A,B,C\}\))。首先显然匹配的这些位置互不相同,而根据 \(M_{AB}\) 的定义有,如果我们把 \(S\) 重复写三遍,那么第 \(i\) 个 \(A\) 的位置必然前于第 \(i+M_{AB}\) 个 B),也就是说第 \(i\) 个 A 的位置早于第 \(i+M_{AB}\) 个 B 的位置,早于第 \(i+M_{AB}+M_{BC}\) 个 C 的位置,早于第 \(i+M_{AB}+M_{BC}+M_{CA}\) 个 A 的位置,而根据 \(M_{AB}+M_{BC}+M_{CA}\le n\) 可知,第 \(i+M_{AB}+M_{BC}+M_{CA}\) 在环上的位置前于第 \(i\) 个 A,也就是我们钦定的三个位置刚好顺着组成了 ABC,对应到序列上也就是 ABC,BCA,CAB 的一种。
因此我们可以写出这样一个 \(n^6\) 的 DP:\(dp_{a,b,c,AB,BC,CA}\) 表示目前有 \(a\) 个 A,\(b\) 个 B,\(c\) 个 C,目前 \(M_{AB},M_{BC},M_{CA}\) 分别是 \(AB,BC,CA\),有多少个符合条件的序列,转移可以做到 \(\Theta(1)\),因此总复杂度就是 \(\Theta(n^6)\)。
AtCoder Grand Contest 055 题解的更多相关文章
- AtCoder Grand Contest 055题解
我太菜啦!!!md,第一题就把我卡死了...感觉对构造题不会再爱了... A - ABC Identity 先来看这个题吧,题意就是给定你一个字符串,让你将这个字符串最多分成6个子串,使得每个字符都在 ...
- AtCoder Grand Contest 017 题解
A - Biscuits 题目: 给出 \(n\) 个物品,每个物品有一个权值. 问有多少种选取方式使得物品权值之和 \(\bmod\space 2\) 为 \(p\). \(n \leq 50\) ...
- Atcoder Grand Contest 054 题解
那天晚上由于毕业晚会与同学吃饭喝酒没打 AGC,第二天稍微补了下题,目前补到了 E,显然 AGC 的 F 对于我来说都是不可做题就没补了(bushi A 简单题,不难发现如果我们通过三次及以上的操作将 ...
- AtCoder Grand Contest 030题解
第一次套刷AtCoder 体验良好 传送门 Poisonous Cookies cout<<b+min(c,a+b+); Tree Burning 难度跨度有点大啊 可以证明当第一次转向之 ...
- AtCoder Grand Contest 031题解
题面 传送门 题解 比赛的之后做完\(AB\)就开始发呆了--简直菜的一笔啊-- \(A - Colorful\ Subsequence\) 如果第\(i\)个字母选,那么它前面任意一个别的字母的选择 ...
- AtCoder Grand Contest 039 题解
传送门 \(A\) 首先只有一串的情况下,遇到相同的肯定是改后面那一个最优,然后两串的话可能要分奇偶讨论一下 //quming #include<bits/stdc++.h> #defin ...
- AtCoder Grand Contest 017题解
传送门 \(A\) 直接转移就是了 typedef long long ll; const int N=55; ll f[N][2];int a[N],n,p; int main(){ scanf(& ...
- AtCoder Grand Contest 015题解
传送门 \(A\) 找到能达到的最大的和最小的,那么中间任意一个都可以被表示出来 typedef long long ll; int n,a,b;ll res; int main(){ scanf(& ...
- AtCoder Grand Contest 038 题解
传送门 这场表现的宛如一个\(zz\) \(A\) 先直接把前\(b\)行全写成\(1\),再把前\(a\)列取反就行 const int N=1005; char mp[N][N];int n,m, ...
随机推荐
- 使用vue-cli+webpack搭建vue开发环境
在这里我真的很开心,好久没有用过博客,今天突然看到了我的博客有不少人看过,虽然没有留下脚印,但是还是激起了我重新拿起博客的信心,感谢大家. 在这里我们需要首先下载node,因为我们要用到npm包下载, ...
- 代码混淆保安全「GitHub 热点速览 v.21.43」
作者:HelloGitHub-小鱼干 虽然让代码难以阅读看似是件难以理解的事情,但是混淆后的代码起到了类似加密的作用,而且经过混淆的代码依旧能实现原代码的功能.javascript-obfuscato ...
- 【UE4 设计模式】组件模式 Components Pattern
概述 描述 在单一实体跨越了多个领域时,为了保持领域之间相互解耦,可以将每部分代码放入各自的组件类中,将实体简化为组件的容器. 套路 参考 UE4中的 Componet 组件使用方式 使用场景 有一个 ...
- 【数据结构与算法Python版学习笔记】图——词梯问题 广度优先搜索 BFS
词梯Word Ladder问题 要求是相邻两个单词之间差异只能是1个字母,如FOOL变SAGE: FOOL >> POOL >> POLL >> POLE > ...
- C# 如何使用代码添加控件及控件事件
1.首先简单设计一下界面: 添加了Click事件 <Window x:Class="WpfApp.MainWindow" xmlns="http://schemas ...
- CentOS 文件管理
目录 目录管理 目录结构 切换目录 查看目录 创建目录 复制目录 剪切目录 删除目录 文件管理 查看文件 创建文件 复制文件 剪切文件 删除文件 创建链接 目录管理 目录也是一种文件. 蓝色目录,绿色 ...
- 易维巡APP技术支持
亲爱的用户 如果您在使用我们的产品时遇到任何问题,请随时与我们联系,我们将全力全意为您解决! 请发邮件与我们联系,我们将24小时为您服务! 电话:18251927768 邮箱地址:xshm999@16 ...
- zuul过滤器filter 的编写
通过上一节(zuul的各种配置)的学习,我们学会了zuul路由的各种配置,这一节我们来实现一下zuul的过滤器功能.那么为什么需要用到zuul的过滤器呢?我们知道zuul是我们实现外部系统统一访问的入 ...
- 算法:N-gram语法
一.N-gram介绍 n元语法(英语:N-gram)指文本中连续出现的n个语词.n元语法模型是基于(n - 1)阶马尔可夫链的一种概率语言模型,通过n个语词出现的概率来推断语句的结构.这一模型被广泛应 ...
- 字符串与模式匹配算法(一):BF算法
一.BF算法的基本思想 BF(Brute Force)算法是模式匹配中最简单.最直观的算法.该算法最基本的思想是从主串的第 start 个字符起和模式P(要检索的子串)的第1个字符比较,如果相等,则逐 ...