POJ 3693 Maximum repetition substring(最多重复次数的子串)
Time Limit: 1000MS | Memory Limit: 65536K | |
Total Submissions: 10461 | Accepted: 3234 |
Description
The repetition number of a string is defined as the maximum number R such that the string can be partitioned into R same consecutive substrings. For example, the repetition number of "ababab" is 3 and "ababa" is 1.
Given a string containing lowercase letters, you are to find a substring of it with maximum repetition number.
Input
The input consists of multiple test cases. Each test case contains exactly one line, which
gives a non-empty string consisting of lowercase letters. The length of the string will not be greater than 100,000.
The last test case is followed by a line containing a '#'.
Output
For each test case, print a line containing the test case number( beginning with 1) followed by the substring of maximum repetition number. If there are multiple substrings of maximum repetition number, print the lexicographically smallest one.
Sample Input
ccabababc
daabbccaa
#
Sample Output
Case 1: ababab
Case 2: aa
题目链接:POJ 3693
把所有可能构成的最多重复次数的子串所对应的循环节大小存下来,然后枚举$SA[i]$与循环节大小,如果刚好枚举到了这个$SA[i]$对应的就是这个循环节大小,那么就是最小的字典序解了,因为$SA[]$是按照字典序排的,当然要注意单个字符这种字符串,因此一开始要把长度定为1。
另外这题数据非常弱,实际上枚举的时候需要加一些边界防止越界问题。可以试一下这些数据:
kabhvlkba
slgnaebbga
lajnbabab
kabkbakbvkab
akbakabka
akjbakjbajkba
akjbakbaiajklbna
kljdfnbisn
akbvkab
答案应该是
a
b
abab
a
a
akjbakjb
a
b
a
代码:
#include <stdio.h>
#include <iostream>
#include <algorithm>
#include <cstdlib>
#include <cstring>
#include <bitset>
#include <string>
#include <stack>
#include <cmath>
#include <queue>
#include <set>
#include <map>
using namespace std;
#define INF 0x3f3f3f3f
#define LC(x) (x<<1)
#define RC(x) ((x<<1)+1)
#define MID(x,y) ((x+y)>>1)
#define fin(name) freopen(name,"r",stdin)
#define fout(name) freopen(name,"w",stdout)
#define CLR(arr,val) memset(arr,val,sizeof(arr))
#define FAST_IO ios::sync_with_stdio(false);cin.tie(0);
typedef pair<int, int> pii;
typedef long long LL;
const double PI = acos(-1.0);
const int N = 100010;
int wa[N], wb[N], cnt[N], sa[N];
int ran[N], height[N];
char s[N];
int pos[N]; inline int cmp(int r[], int a, int b, int d)
{
return r[a] == r[b] && r[a + d] == r[b + d];
}
void DA(int n, int m)
{
int i;
int *x = wa, *y = wb;
for (i = 0; i < m; ++i)
cnt[i] = 0;
for (i = 0; i < n; ++i)
++cnt[x[i] = s[i]];
for (i = 1; i < m; ++i)
cnt[i] += cnt[i - 1];
for (i = n - 1; i >= 0; --i)
sa[--cnt[x[i]]] = i;
for (int k = 1; k <= n; k <<= 1)
{
int p = 0;
for (i = n - k; i < n; ++i)
y[p++] = i;
for (i = 0; i < n; ++i)
if (sa[i] >= k)
y[p++] = sa[i] - k;
for (i = 0; i < m; ++i)
cnt[i] = 0;
for (i = 0; i < n; ++i)
++cnt[x[y[i]]];
for (i = 1; i < m; ++i)
cnt[i] += cnt[i - 1];
for (i = n - 1; i >= 0; --i)
sa[--cnt[x[y[i]]]] = y[i];
swap(x, y);
x[sa[0]] = 0;
p = 1;
for (i = 1; i < n; ++i)
x[sa[i]] = cmp(y, sa[i - 1], sa[i], k) ? p - 1 : p++;
m = p;
if (m >= n)
break;
}
}
void gethgt(int n)
{
int i, k = 0;
for (i = 1; i <= n; ++i)
ran[sa[i]] = i;
for (i = 0; i < n; ++i)
{
if (k)
--k;
int j = sa[ran[i] - 1];
while (s[j + k] == s[i + k])
++k;
height[ran[i]] = k;
}
}
namespace SG
{
int dp[N][17];
void init(int l, int r)
{
int i, j;
for (i = l; i <= r; ++i)
dp[i][0] = height[i];
for (j = 1; l + (1 << j) - 1 <= r; ++j)
{
for (i = l; i + (1 << j) - 1 <= r; ++i)
dp[i][j] = min(dp[i][j - 1], dp[i + (1 << (j - 1))][j - 1]);
}
}
int ask(int l, int r)
{
int len = r - l + 1;
int k = 0;
while (1 << (k + 1) <= len)
++k;
return min(dp[l][k], dp[r - (1 << k) + 1][k]);
}
int LCP(int l, int r, int len)
{
l = ran[l], r = ran[r];
if (l > r)
swap(l, r);
if (l == r)
return len - sa[l];
return ask(l + 1, r);
}
}
int main(void)
{
int T = 0, len, i, j;
while (~scanf("%s", s) && s[0] != '#')
{
len = strlen(s);
DA(len + 1, 130);
gethgt(len);
SG::init(1, len);
int ans = 1;
int sz = 0;
for (int L = 1; L < len; ++L)
{
for (i = 0; i + L < len; i += L)
{
int lcp = SG::LCP(i, i + L, len);
int cnt = lcp / L + 1;
int j = i - (L - lcp % L);
if (j >= 0 && lcp % L != 0 && SG::LCP(j , j + L, len) / L + 1 > cnt)
++cnt;
if (cnt > ans)
{
ans = cnt;
sz = 0;
pos[sz++] = L;
}
else if (cnt == ans)
pos[sz++] = L;
}
}
int length = 1;
int st = 0;
int flag = 0;
for (i = 1; i <= len && !flag; ++i)
{
for (j = 0; j < sz; ++j)
{
int unit = pos[j];
if (sa[i] + unit < len && SG::LCP(sa[i], sa[i] + unit, len) >= (ans - 1) * unit)
{
length = ans * unit;
st = sa[i];
flag = 1;
break;
}
}
}
printf("Case %d: ", ++T);
for (i = st; i < st + length; ++i)
putchar(s[i]);
puts("");
}
return 0;
}
POJ 3693 Maximum repetition substring(最多重复次数的子串)的更多相关文章
- POJ-3693/HDU-2459 Maximum repetition substring 最多重复次数的子串(需要输出具体子串,按字典序)
http://acm.hdu.edu.cn/showproblem.php?pid=2459 之前hihocoder那题可以算出最多重复次数,但是没有输出子串.一开始以为只要基于那个,每次更新答案的时 ...
- POJ - 3693 Maximum repetition substring(重复次数最多的连续重复子串)
传送门:POJ - 3693 题意:给你一个字符串,求重复次数最多的连续重复子串,如果有一样的,取字典序小的字符串. 题解: 比较容易理解的部分就是枚举长度为L,然后看长度为L的字符串最多连续出现 ...
- poj 3693 Maximum repetition substring 重复次数最多的连续子串
题目链接 题意 对于任意的字符串,定义它的 重复次数 为:它最多可被划分成的完全相同的子串个数.例如:ababab 的重复次数为3,ababa 的重复次数为1. 现给定一字符串,求它的一个子串,其重复 ...
- POJ 3693 Maximum repetition substring(连续重复子串)
http://poj.org/problem?id=3693 题意:给定一个字符串,求重复次数最多的连续重复子串. 思路: 这道题确实是搞了很久,首先枚举连续子串的长度L,那么子串肯定包含了r[k], ...
- POJ 3693 Maximum repetition substring(后缀数组)
Description The repetition number of a string is defined as the maximum number R such that the strin ...
- POJ 3693 Maximum repetition substring(后缀数组+ST表)
[题目链接] poj.org/problem?id=3693 [题目大意] 求一个串重复次数最多的连续重复子串并输出,要求字典序最小. [题解] 考虑错位匹配,设重复部分长度为l,记s[i]和s[i+ ...
- 后缀数组 POJ 3693 Maximum repetition substring
题目链接 题意:给定一个字符串,求重复次数最多的连续重复子串. 分析:(论文上的分析)先穷举长度 L,然后求长度为 L 的子串最多能连续出现几次.首先连续出现 1 次是肯定可以的,所以这里只考虑至少 ...
- poj 3693 Maximum repetition substring (后缀数组)
其实是论文题.. 题意:求一个字符串中,能由单位串repeat得到的子串中,单位串重复次数最多的子串.若有多个重复次数相同的,输出字典序最小的那个. 解题思路:其实跟论文差不多,我看了很久没看懂,后来 ...
- POJ 3693 Maximum repetition substring ——后缀数组
重复次数最多的字串,我们可以枚举循环节的长度. 然后正反两次LCP,然后发现如果长度%L有剩余的情况时,答案是在一个区间内的. 所以需要找到区间内最小的rk值. 两个后缀数组,四个ST表,$\Thet ...
随机推荐
- Ubuntu16.04采用FastCGI方式部署Flask web框架
1 部署nginx 1.1 安装nginx服务 root@desktop:~# apt-get install nginx -y 1.2 验证nginx服务是否启动 root@des ...
- 三角形div原理(小知识点)
三角形div其实就是从边框的演变过程 #sider2{ width: 100px; height: 100px; border-top: 30px solid #000; border-right: ...
- Asp.NET Core 在IIS部署 An assembly specified in the application dependencies manifest was not found
今天在发布应用的时候,出来了一个报错:An assembly specified in the application dependencies manifest was not found 情况如下 ...
- git上下载的thinkphp框架报错解决方法
git上下载的thinkphp5框架使用.gitignore没上传依赖,需要通过composer进行下载依赖,使用composer install或者composer update即可解决.
- Jupyter Notebook里面使用Matplotlib画图 图表中文乱码问题
可查看以下链接: https://blog.csdn.net/ccblogger/article/details/79613335
- Nginx一直报504超时,配置相关参数好了
相关参数:large_client_header_buffers 4 16k;client_max_body_size 30m;client_body_buffer_size 128k;proxy_c ...
- Linux/CentOS防CC攻击脚本
#!/bin/sh cd /var/log/httpd/ cat access_log|awk > a cp /dev/null access_log cp /dev/null error_lo ...
- LeetCode题目解答
LeetCode题目解答——Easy部分 Posted on 2014 年 11 月 3 日 by 四火 [Updated on 9/22/2017] 如今回头看来,里面很多做法都不是最佳的,有的从复 ...
- define 和 const常量有什么区别?
define在预处理阶段进行替换,const常量在编译阶段使用 宏不做类型检查,仅仅进行替换,const常量有数据类型,会执行类型检查 define不能调试,const常量可以调试 define定义的 ...
- webpack loader之css、scss、less、stylus安装
1.打包css,需要安装css-loader和style-loader yarn add --dev css-loader style-loader 或者 npm install --save-dev ...