CodeForces 126B Password 【kmp】
2016-10-14 13:13
399 查看
题目:点击打开链接
题意:给出一个字符串,求出最长相同的的前缀子串和后缀子串,使得字符串中也存在该子串(不包括前缀子串和后缀子串)。
思路:显然先将字符串处理出next数组,由于next数组保存的是最长公共前后缀长度减一(即要跳转的那一位),所以字符串最后一位字符存的是大于等于满足条件的子串长度,然后要找到中间的子串,从后往前扫一遍字符串直到最长前缀,若发现next值等于最后一个字符的next值,则该值可能是最长长度,先记录下来,然后观察最后一个字符跳转的位置是否能再次跳转,若可以,则继续往前扫,若某位的next值等于最后一个字符跳转的那个位置的next值,则说明存在相同后缀,记录下其next值,最后综上用最大的next值表示答案子串的长度减一,输出前缀子串即可。
代码:
#include <stdio.h>
#include <cstring>
#include <cmath>
#include <algorithm>
#include <queue>
#include <set>
#include <vector>
#include <map>
#define PR pair<int,int>
#define MP make_pair
#define fi first
#define se second
#define lson l,m,rt<<1
#define rson m+1,r,rt<<1|1
#define sqr(x) ((x)*(x))
#define ll long long
#define ull unsigned __int64
const ll INF = 1e18;
const int inf=0x3f3f3f3f;
const int M=200010;
const int N=1000100;
const int MOD=10007;
const double eps=1e-10;
const double pi=acos(-1.0);
using namespace std;
char a
;
int n,nxt
;
int main()
{
int i,j;
scanf("%s",a);
n=strlen(a);
nxt[0]=-1;
for(i=1;i<n;i++)
{
j=nxt[i-1];
while(j>=0&&a[i]!=a[j+1]) j=nxt[j];
nxt[i]=a[i]==a[j+1]?j+1:-1;
}
if(nxt[n-1]==-1) {puts("Just a legend");return 0;}
int ok=0,ans=0;
for(i=n-2;i>nxt[n-1];i--)
{
if(nxt[i]==nxt[n-1]) ok=1,ans=nxt[n-1];
}
if(nxt[nxt[n-1]]!=-1)
{
for(i=nxt[n-1];i>nxt[nxt[n-1]];i--)
{
if(nxt[i]==nxt[nxt[n-1]]) ok=1,ans=max(ans,nxt[nxt[n-1]]);
}
}
if(ok==0) puts("Just a legend");
else
{
for(i=0;i<=ans;i++) printf("%c",a[i]);puts("");
}
}
题意:给出一个字符串,求出最长相同的的前缀子串和后缀子串,使得字符串中也存在该子串(不包括前缀子串和后缀子串)。
思路:显然先将字符串处理出next数组,由于next数组保存的是最长公共前后缀长度减一(即要跳转的那一位),所以字符串最后一位字符存的是大于等于满足条件的子串长度,然后要找到中间的子串,从后往前扫一遍字符串直到最长前缀,若发现next值等于最后一个字符的next值,则该值可能是最长长度,先记录下来,然后观察最后一个字符跳转的位置是否能再次跳转,若可以,则继续往前扫,若某位的next值等于最后一个字符跳转的那个位置的next值,则说明存在相同后缀,记录下其next值,最后综上用最大的next值表示答案子串的长度减一,输出前缀子串即可。
代码:
#include <stdio.h>
#include <cstring>
#include <cmath>
#include <algorithm>
#include <queue>
#include <set>
#include <vector>
#include <map>
#define PR pair<int,int>
#define MP make_pair
#define fi first
#define se second
#define lson l,m,rt<<1
#define rson m+1,r,rt<<1|1
#define sqr(x) ((x)*(x))
#define ll long long
#define ull unsigned __int64
const ll INF = 1e18;
const int inf=0x3f3f3f3f;
const int M=200010;
const int N=1000100;
const int MOD=10007;
const double eps=1e-10;
const double pi=acos(-1.0);
using namespace std;
char a
;
int n,nxt
;
int main()
{
int i,j;
scanf("%s",a);
n=strlen(a);
nxt[0]=-1;
for(i=1;i<n;i++)
{
j=nxt[i-1];
while(j>=0&&a[i]!=a[j+1]) j=nxt[j];
nxt[i]=a[i]==a[j+1]?j+1:-1;
}
if(nxt[n-1]==-1) {puts("Just a legend");return 0;}
int ok=0,ans=0;
for(i=n-2;i>nxt[n-1];i--)
{
if(nxt[i]==nxt[n-1]) ok=1,ans=nxt[n-1];
}
if(nxt[nxt[n-1]]!=-1)
{
for(i=nxt[n-1];i>nxt[nxt[n-1]];i--)
{
if(nxt[i]==nxt[nxt[n-1]]) ok=1,ans=max(ans,nxt[nxt[n-1]]);
}
}
if(ok==0) puts("Just a legend");
else
{
for(i=0;i<=ans;i++) printf("%c",a[i]);puts("");
}
}
相关文章推荐
- codeforces 126B password KMP
- codeforces 126B password[kmp]
- codeforces 126B Password KMP
- CodeForces 126B password KMP
- Codeforces 126B Password(KMP)
- codeforces 126B Password (kmp,next应用)
- Codeforces 126B Password- z-box算法
- Password CodeForces - 126B [KMP+DP思维]
- [KMP][字符串Hash] #93 div1 cf 126B Password
- CodeForces 126B - Password 利用KMP
- codeforces 126B Password - Z-Box算法
- codeforces 126B B. Password(kmp+dp)
- codeforces 126B Password
- codeforces 182D Common Divisors (kmp,next应用)
- Codeforces Beta Round #93 (Div. 1 Only)-B. Password(KMP)
- CodeForces 25E Test KMP
- Codeforces 535D - Tavas and Malekas【KMP】
- CodeForces 432D|Prefixes and Suffixes|KMP|动态规划
- Codeforces 631D Messenger KMP
- codeforces 432D Prefixes and Suffixes (kmp+dp)