[AGC027E]ABBreviate
Description
AGC027E
给定一个仅由\(AB\)构成的字符串\(S\),给定两个操作,把\(AA\)换成\(B\),和把\(BB\)换成\(A\),问由这个字符串和任意次操作可以得到几种字符串。
Solution
AGC好难啊(摔
首先,如果不能操作,答案是\(0\)。
我们令\(A=1,B=2\),这样就会有一个美妙的性质:所有字符的和在操作的时候在模\(3\)意义下不变,我们记这个和为\(p(S)\)。然后我们可以得到一个结论:一个字符串\(S\)可以变成字符\(c\),当且仅当:\(S=c\)或\(p(S)=p(c)\)且\(S\)可以操作。这个条件的必要性很好证明,而充分性证明也比较简单:当\(S\)中的连续字符长度为\(2\)时,可以合并这两个字符,并且字符串长度减小;而当\(S\)中的连续字符长度大于\(2\)时,可以合并与不同字符相邻的那一端的字符(如果只有一种字符的话,自己证吧),字符串长度也减少;这样,字符串长度不断减少,一定可以达到\(1\),这时的\(S'=c\)。
这样问题就转化为:求出这样的\(T\)的数量:将\(S\)划分为\(|T|\)段,第\(i\)段的\(p\)值与\(T\)中的第\(i\)个字符的\(p\)值相等。我们可以贪心的构造这样的\(T\):让每一段的长度尽可能的小,如果分出\(|T|\)段后,剩余部分的\(p\)值为\(0\),那就是一个合法的\(T\)。
这样,就只需要一个简单的DP就行了我们递推的来做,\(f_i\)表示前\(i\)个字符看作一段的方案数,如果\(p(S_{i+1,n})=0\),那么\(i\)之后的位置可以看成是剩余的位置,\(f_i\)的初值为\(1\),否则为\(0\)。然后,我们可以在\(i\)之后加一段\(A\)或是\(B\),这样就要记录各个\(p\)值最后一次出现的位置,累加即可。具体实现看代码。
Code
#include <cstdio>
const int N = 1e5 + 10;
const int MOD = 1e9 + 7;
char s[N];
int a[N], n, f[N], nxt[3];
int main() {
scanf("%s", s);
for (; s[n]; ++n) a[n+1] = (a[n] + s[n] - 'a' + 1) % 3; // 求前缀和
// 判断是否可以操作
int flag = 0;
for (int i = 1; i < n; ++i) {
if (s[i] == s[i-1]) flag = 1;
}
if (!flag) {
puts("1");
return 0;
}
// 递推
f[n] = 1;
for (int i = 0; i < 3; ++i) nxt[i] = i == a[n] ? n : n + 1;
for (int i = n-1; i; --i) {
f[i] = a[i] == a[n]; // 后面可不可以不分段
for (int c = 1; c <= 2; ++c) {
(f[i] += f[nxt[(a[i]+c)%3]]) %= MOD; // 后面加一段A或B
}
nxt[a[i]] = i; // 记录该p值最后一次出现的位置
}
printf("%d\n", (f[nxt[1]] + f[nxt[2]]) % MOD);
return 0;
}
[AGC027E]ABBreviate的更多相关文章
- AGC027 E - ABBreviate
目录 题目链接 题解 代码 题目链接 AGC027 E - ABBreviate 题解 神仙啊 建议查看https://img.atcoder.jp/agc027/editorial.pdf 定义a ...
- java stopwatch 功能
C#中有一个stopwatch的功能,主要是用来监测程序执行时间的.java之前一直都在用如下方式完成: public static void main(String[] args) { long s ...
- gradle学习笔记
一直想着花时间学习下gradle,今天有空.入门一下.参考:极客学院gradle使用指南,官方文档:gradle-2.12/docs/userguide/installation.html,以及百度阅 ...
- Linux监控工具介绍系列——smem
smem工具介绍 smem是Linux系统上的一款可以生成多种内存耗用报告的命令行工具.与现有工具不一样的是smem可以报告实际使用的物理内存(PSS),这是一种更有意义的指标.可以衡量虚拟内存系统的 ...
- StringUtils工具类
StringUtils源码,使用的是commons-lang3-3.1包.下载地址 http://commons.apache.org/lang/download_lang.cgi 以下是String ...
- POJ2001Shortest Prefixes[Trie]
Shortest Prefixes Time Limit: 1000MS Memory Limit: 30000K Total Submissions: 17683 Accepted: 768 ...
- StringUtils中的常用的方法
org.apache.commons.lang.StringUtils中常用的方法,这里主要列举String中没有,且比较有用的方法: 1. 检查字符串是否为空: static boolean isB ...
- Google C++ Style Guide
Background C++ is one of the main development languages used by many of Google's open-source project ...
- Apache Commons Lang
http://commons.apache.org/proper/commons-lang/javadocs/api-release/org/apache/commons/lang3/package- ...
随机推荐
- 权限问题 <customErrors> 标记的“mode”属性设置为“Off”
引用 权限问题 <customErrors> 标记的“mode”属性设置为“Off”. 权限问题标记的“mode”属性设置为“Off”.说明: 服务器上出现应用程序错误.此应用程序的当前自 ...
- 爬虫学习笔记2requests库和beautifulsoup4库学习笔记
目录 1.requests库 1.1 安装 2.beautifulsoup4 2.1 常用方法 2.2 bs4 中四大对象种类 2.3 遍历文档树 2.4 搜索文档树 查询id=head的Tag 查询 ...
- 机器学习作业(四)神经网络参数的拟合——Matlab实现
题目下载[传送门] 题目简述:识别图片中的数字,训练该模型,求参数θ. 第1步:读取数据文件: %% Setup the parameters you will use for this exerci ...
- 互联网的“ip分组交换技术”
(1)从名字分析 从“ip分组交换”这个名字中,我们看看涉及哪些事情. 1)交换 主要涉及两类交换. · 交换机:负责网内部数据交换 · 路由器:负责网间的数据交换. ip分组交换技术的核心就是路由器 ...
- 为什么要使用NoSQL数据库
NoSQL概念 随着web2.0的快速发展,非关系型.分布式数据存储得到了快速的发展,它们不保证关系数据的ACID特性(原子性.一致性.隔离性.持久性,一个支持事务的数据库,必需要具有这四种特性,否则 ...
- Mac使用pip命令安装selenium包报错解决方法
1.使用命令: pip install selenium 2.换成命令: python -m pip install selenium 即可成功安装
- Java时间格式字符串与Date的相互转化
目录 将Date转化为格式化字符串 时间格式字符串转化为Date @ 将Date转化为格式化字符串 将Date转化为格式化字符串是利用SimpleDateFormat类继承自 java.text.Da ...
- android 代码实现模拟用户点击、滑动等操作
/** * 模拟用户点击 * * @param view 要触发操作的view * @param x 相对于要操作view的左上角x轴偏移量 * @param y 相对于要操作view的左上角y轴偏移 ...
- android 直接添加一个Fragment到activity,不需要额外setContentView
getSupportFragmentManager().beginTransaction().replace(android.R.id.content,new ArticleListFragment( ...
- opencv:程序运行完保持dos窗口不关闭
(1)在main函数最后加上 system("pause"); 第一种不能加到含有imshow图片显示的结尾:否则会不能显示图片: (2)利用cvWaitKey()函数: 这种能加 ...