题目链接:
http://acm.hdu.edu.cn/showproblem.php?pid=2203
题目大意:
给定亲和串的定义:给定两个字符串s1和s2,如果能通过s1循环移位,使s2包含在s1中,
那么我们就说s2 是s1的亲和串。现在给你两个字符串s1和s2,判断s2是否是s1的亲和串。
思路:
先判断s2的串长度是否小于等于s1的长度,因为如果s2的串长度比s1还要长的话,s2是不
可能是s1的亲和串。然后在s1的串后边在街上s1的串,对s1和s2进行KMP算法,看s1的串
中是否包含s2的串,如果包含,则s2就是s1的亲和串,否则就不是亲和串。
AC代码:
# include<stdio.h>
# include<string.h>
char a[200010],b[100010];
int next[100010];
void getnext(char *pat)
{
int len_pat = strlen(pat);
int i = 0;
int j = -1;
next[0] = -1;
while(i < len_pat)
{
if(j == -1 || pat[i] == pat[j])
{
i++;
j++;
next[i] = j;
}
else
j = next[j];
}
}
int KMP(char *str, char *pat)
{
int i = 0;
int j = 0;
int len_str = strlen(str);
int len_pat = strlen(pat);
getnext(pat);
while(i < len_str)
{
if(j == -1 || str[i] == pat[j])
{
i++;
j++;
}
else
j = next[j];
if(j >= len_pat)
return 1;
}
return 0;
}
int main()
{
int len_a,len_b,i;
while(~scanf("%s%s",a,b))
{
len_a = strlen(a);
len_b = strlen(b);
if(len_a < len_b)
{
printf("no\n");
continue;
}
for(i = 0; i <len_a; i++)
a[i+len_a] = a[i];
a[i+len_a] = '\0';
if(!KMP(a,b))
printf("no\n");
else
printf("yes\n");
}
return 0;
}