这是最近举行的编程竞赛的一个问题。
当且仅当存在偏移d时,两个字符串a [0..n-1]和b [0..n-1]被称为循环等效,使得对于所有0< = i< n,a [i] = b [(i + d)mod n]。 给定两个字符串s [0..L-1]和t [0..L-1]具有相同的长度L.你需要找到最大p,使得s [0..p-1]和t [0。 .p-1]是循环等价的。如果没有这样的有效p,则打印0。
输入
第一行包含一个整数T,表示测试用例的数量。 对于每个测试用例,总共有两行。第一行包含s。第二行包含t。 所有字符串仅包含小写字母。
输出
总共输出T行。每行应以" Case#:"开头。然后是最大值p。在这里"#"是从1开始的测试用例的编号。 约束
1≤T≤10 1≤L≤1000000
示例
输入:
2
ABAB
巴巴
ABAB
BAAC
输出:
案例1:4
案例2:3
解释
案例1,d可以是1.
案例2,d可以是2。
我的方法:
在S [0 ... i],T [0 ... i]中生成S和T的所有子串,并将S [0 ... i]连接到自身,并检查T是否为子串S [0 ... 1] + S [0 ... i]中。如果是子串,则最大P = i
bool isCyclic( string s, string t ){
string str = s;
str.append(s);
if( str.find(t) != string::npos )
return true;
return false;
}
int main(){
string s, t;
int t1,l, o=1;
scanf("%d", &t1);
while( t1-- ){
cin>>s>>t;
l = min( s.length(), t.length());
int i, maxP = 0;
for( i=1; i<=l; i++ ){
if( isCyclic(s.substr(0,i), t.substr(0,i)) ){
maxP = i;
}
}
printf("Case %d: %d\n", o++, maxP);
}
return 0;
}
我知道这不是解决此问题的最优化方法,因为我超时限制。我开始知道前缀函数可用于获取O(n)算法。我不知道前缀功能。有人可以解释O(n)方法吗? 比赛链接http://www.codechef.com/ACMKGP14/problems/ACM14KP3