E. String Multiplication

题意

分析:

  从后往前考虑字符串变成什么样子。

  设$S_i = p_1 \cdot p_2 \dots p_{i}$,最后一定是$S_{n - 1} \cdot p_n$,就是将$S_{n-1}$每两个字符之间放入$p_n$。按照$p_n$分类讨论,那么最后有三种情况。

  设$p_n$的开头字符是$c0$,结尾字符是$c1$,包含开头的连续段的长度是$len0$,包含结尾的连续段的长度是$len1$。

  1、$c0 \neq c1$,那么答案可以是三个:(1).可以是$p_n$中最长的连续子段;(2).如果$S_{n-1}$中存在$c0$,$len0+1$;(3).如果$S_{n-1}$中存在$c1$,$len1+1$。

  2、$c0 = c1$,并且整个串不只有一种字符:如果$S_{n-1}$中存在$c0$,那么答案可以是$len0+len1+1$

  3、如果$p_n$只有一种字符构成,那么求$S_{n-1}$中最长的字符是$c0$连续段的,设为t,答案是$(t+1) \times len + t$。

  可以递归查询。

代码:

#include<cstdio>
#include<algorithm>
#include<cstring>
#include<iostream>
#include<cmath>
#include<cctype>
#include<set>
#include<queue>
#include<vector>
#include<map>
using namespace std;
typedef long long LL; inline int read() {
int x=,f=;char ch=getchar();for(;!isdigit(ch);ch=getchar())if(ch=='-')f=-;
for(;isdigit(ch);ch=getchar())x=x*+ch-'';return x*f;
} const int N = ;
string s[N];
bool a[N][], b[N]; LL dfs(int x,char c) {
if (x == ) return ;
int ans = a[x - ][c - 'a'], sz = s[x].size();
if (b[x] && s[x][] == c) {
ans = dfs(x - , c);
return (ans + ) * sz + ans;
}
else {
int q = , h = , last = -;
for (int i = ; i < sz; ++i) {
if (s[x][i] == c && last == -) last = i;
if (s[x][i] == c) ans = max(ans, i - last + );
else last = -;
}
for (int i = ; i < sz; ++i) {
if (s[x][i] == c) q ++; else break;
}
for (int i = sz - ; ~i; --i) {
if (s[x][i] == c) h ++; else break;
}
if (s[x][] == c && s[x - ][sz - ] == s[x][] && a[x - ][c - 'a']) ans = max(ans, q + h + );
if (s[x][] == c && a[x - ][c - 'a']) ans = max(ans, q + );
if (s[x][sz - ] == c && a[x - ][c - 'a']) ans = max(ans, h + );
if (s[x][] == c) ans = max(ans, q);
if (s[x][sz - ] == c) ans = max(ans, h);
return ans;
}
}
int main() {
int n = read();
for (int i = ; i <= n; ++i) cin >> s[i], b[i] = ;
for (int i = ; i <= n; ++i) {
for (int j = ; j < (int)s[i].size(); ++j) if (s[i][j] != s[i][j - ]) { b[i] = ; break; }
for (int j = ; j < (int)s[i].size(); ++j) a[i][s[i][j] - 'a'] = ;
for (int j = ; j < ; ++j) a[i][j] |= a[i - ][j];
}
int ans = , q = , h = , last = , sz = s[n].size();
for (int i = ; i < sz; ++i) {
if (last == && s[n][i] == s[n][]) q ++;
if (s[n][i] == s[n][last]) ans = max(ans, i - last + );
else last = i;
}
for (int i = sz - ; i >= ; --i) {
if (s[n][i] == s[n][sz - ]) h ++;
else break;
}
if (!b[n]) {
if (s[n][] == s[n][sz - ] && a[n - ][s[n][] - 'a']) ans = max(ans, q + h + );
if (a[n - ][s[n][] - 'a']) ans = max(ans, q + );
if (a[n - ][s[n][sz - ] - 'a']) ans = max(ans, h + );
ans = max(ans, max(q, h));
cout << ans;
return ;
}
int t = dfs(n - , s[n][]);
cout << (t + ) * sz + t;
return ;
}

CF 1131 E. String Multiplication的更多相关文章

  1. CF #541 E. String Multiplication

    题意: 给定一系列字符串,每次都是后一个字符串和前面的融合,这个融合操作就是原来的串分成独立的,然后把新串插入到这些空格中.问最后,最长的相同连续的长度. 思路: 这道题可以贪心的来,我们压缩状态,记 ...

  2. Codeforces #541 (Div2) - E. String Multiplication(动态规划)

    Problem   Codeforces #541 (Div2) - E. String Multiplication Time Limit: 2000 mSec Problem Descriptio ...

  3. E. String Multiplication

    E. String Multiplication time limit per test 2 seconds memory limit per test 256 megabytes input sta ...

  4. CF1131E String Multiplication(???)

    这题难度2200,应该值了. 题目链接:CF原网 题目大意:定义两个字符串 $s$ 和 $t$($s$ 的长度为 $m$)的乘积为 $t+s_1+t+s_2+\dots+t+s_m+t$.定义一个字符 ...

  5. CF 1003B Binary String Constructing 【构造/找规律/分类讨论】

    You are given three integers a, b and x. Your task is to construct a binary string s of length n=a+b ...

  6. CF 1140B Good String

    Description You have a string ss of length nn consisting of only characters > and <. You may d ...

  7. 【CF 710F】String Set Queries

    在校内OJ上A了,没有加强制在线的东西..不放链接了. 这道题题意是维护一个字符串集合,支持三种操作: 1.加字符串 2.删字符串 3.查询集合中的所有字符串在给出的模板串中出现的次数 操作数\(m ...

  8. CF 827E Rusty String FFT

    传送门 如果没有碍事的?的话,判定字符串的循环节直接用KMP的失配数组就可以搞定.现在有了碍事的?,我们就需要考虑更通用的算法. 考虑KMP失配数组判定字符串循环节的本质,发现判定\(k\)是否为字符 ...

  9. CF - 1131 D Gourmet choice

    题目传送门 先把 = 的人用并查集合并在一起. 然后 < > 的建边, 跑一遍 toposort 之后就好了. 入度为0点的值肯定为1, 然后就是因为这个是按照时间线走过来的,所以一个点的 ...

随机推荐

  1. 【转】PyDev Eclipse使用技巧说明

    PyDev Package Explorer 创建项目 在开展工作之前,需要创建一个新的项目.在 Eclipse 菜单栏中,选择 File > New > Project > Pyd ...

  2. freeRTOS中文实用教程5--内存管理

    1.前言 不同的嵌入式系统具有不同的内存配置和时间要求.所以单一的内存分配算法只可能适合部分应用程序. FreeRTOS 将内存分配作为可移植层面(相对于基本的内核代码部分而言).这使得不同的应用程序 ...

  3. DataSnap ClientdataSet 三层中主从表的操作

    非原创  摘自:http://hi.baidu.com/yagzh2000/blog/item/fc69df2cb9845de78b139946.html三层中主从表的操作(删除.新增.修改)一定要在 ...

  4. java多线程系列五、并发容器

    一.ConcurrentHashMap 1.为什么要使用ConcurrentHashMap 在多线程环境下,使用HashMap进行put操作会引起死循环,导致CPU利用率接近100%,HashMap在 ...

  5. grep基础用法

    功能:全面搜索正则表达式并把行打印出来,是一种强大的文本搜索工具. grep  yuan  filename :在文件中搜索yuan 这个字符串,并把含有此字符串的行打印出来,也可以多文件搜索.  g ...

  6. 模拟js中注册表单验证

    示例1 <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8 ...

  7. apache tomcat 集群!

    公司需要一个内部测试局域网, 要求可以支持3000并发访问!以前也没做过服务器这方面.临时抱佛脚,查看了N多文档,他人经验,布置好之后,又遇到了N多问题,功夫不负有心人.终于还是完成了要求!观他人的布 ...

  8. String对象的常用属性和方法

    属性 描述 length 在大多数情况下返回字符串中的字符数 方法 描述 toUpperCase() 将字符串修改为大写字母 toLowerCase() 将字符串修改为小写字母 charAt() 以索 ...

  9. 使用spring-boot-starter-data-jpa 怎么配置使运行时输出SQL语句

    在 application.properties 中加入以下配置 spring.jpa.show-sql=true

  10. [ZJOI2011]最小割

    题解: 以前看过,思维挺神奇的一道题目 首先可以证明最小割是不能相交的 那么我们就可以找到任意两点求一次最小割然后将割的两边分开来再递归这个过程 另外最小割就是vis=0与vis=1之间的连边 分治的 ...