题目链接:
https://vjudge.net/problem/1810469/origin
题目大意:
给你一个字符串,中间切一刀,左右两边均反转,然后右边的串拼接到左边上。
思路:
比如 aabb | cc --> ccbbaa, 这是一个反转的例子
如果 aabbcc| -> aabbcc, |aabbcc -> ccbbaa 考虑极端情况,知道,这相当于一个环!
于是就有做出一个重复字符串的思路,遍历一遍就可以了。
下面是AC代码:
#include <iostream> #include <cstdio> #include <string.h> using namespace std; const int MX = 2e5+10; char s[MX]; int main() { int ans = -1; int cnt = 1, j; scanf("%s", s+1); int n = strlen(s+1); for(int i = 1; i <= n; ++i) s[n+i] = s[i]; for(int i = 1; i <= 2*n; i = j) // 注意i = j跳步 { cnt = 1; for(j = i+1; j <= 2*n; ++j) { if(s[j-1] != s[j]) cnt++; //若不同则串长度加一! else break; //相同则停止 } ans = max(ans, cnt); } ans = min(ans, n); //这句话一定要加。。,可能大于n! printf("%d ", ans); }
上面的代码用了两个for循环,并且优化了一下,一个学长的代码一个for循环就可以了,而且不用再弄一个数组:
#include <iostream> #include <cstdio> #include <string.h> using namespace std; const int MX = 1e5+10; char s[MX]; int main() { int ans = -1; int cnt = 1; scanf("%s", s); // 如果用s+1则会在后面的串里多一个空格!所以出错 int n = strlen(s); for(int i = 1; i < 2*n; ++i) { if(s[i%n] != s[(i-1)%n]) cnt++; // s+1的时候会导致出错! else { ans = max(ans, cnt); cnt = 1; } ans = max(ans, cnt); } ans = min(ans, n); printf("%d ", ans); }
注意!用取模运算代替循环数组下标最好从0开始!!!
如有疑问,欢迎评论指出!