市面上最常见的魔方,是三阶魔方,英文名为Rubik‘s Cube,以魔方的发明者鲁比克教授的名字命名。另外,二阶魔方叫Pocket Cube,它只有2*2*2个角块,通常也就比较小;四阶魔方叫Revenge Cube,这是因为就算你好不容易复原了三阶魔方,四阶魔方也会向你“复仇”;而五阶魔方叫Professor Cube,人们认为只有专家才能够复原这么复杂的魔方。
作为ACM(A Cube Master),squee_spoon准备为九阶正十二面体魔方命名,此时他的脑中浮现出一个长长的字符串S,似乎可以作为魔方的英文名。但是问题没有那么简单,squee_spoon有n个不喜欢的短字符串a1~an,所以squee_spoon希望将九阶正十二面体魔方命名为S的最长子串T,在这个子串中,不能包含a1~an,即a1~an均不是T的子串。
Input
多组数据。
第一行,字符串S,长度不会超过10^5。
第二行,一个整数n,1<=n<=10。
接下来的n行,n个字符串a1~an,ai的长度不会超过10。
Output
对于每组数据,输出两个整数,分别是T的长度及其在原串S中的起始下标(下标从0开始,如果存在多解,输出最小的起始下标)。
Sample Input
orz_zzuspy 2 orz us YM_2030xxj 3 _20 03 M_
Sample Output
6 1 5 5
HINT
Source
和之前做的一道题几乎一样,但是上次那道题太水,错的代码交了也是对的;
#include<stdio.h> #include<string.h> #include<algorithm> #include<queue> #define N 100010 using namespace std; struct node { int L, R; } a[N]; char s[N]; int cmp(node p, node q) { if(p.L!=q.L) return p.L<q.L; return p.R<q.R; } int main() { char s0[N]; int n,k, Len; while(scanf("%s", s)!=EOF) { memset(a, 0, sizeof(a)); Len=strlen(s); scanf("%d", &n); k=1; for(int i=1; i<=n; i++) { scanf("%s", s0); if(strstr(s, s0)!=NULL) { int pos = 0; int len = 0; while(strstr(s+pos+len, s0)!=NULL) { pos = strstr(s+pos+len, s0)-s; len = strlen(s0); a[k].L=pos; a[k++].R = pos+len-1; len=1;///查找时要考虑以下数据:回文串; } } } sort(a+1, a+k, cmp); a[k].L=0, a[k].R = Len;///防止出现k=1的情况; int Max=0, Index=-1; for(int i=2; i<k; i++) { int len1=a[i].R-a[i-1].L-1; int len2=a[i-1].R-a[i].L-1;///如果a[i].R<a[i-1].R; if(len1>Max) { Max = len1; Index = a[i-1].L+1; } if(len2>Max) { Max = len2; Index = a[i].L+1; } } if(a[1].R>=Max)///与开头和结尾的相比较; { Max = a[1].R; Index = 0; } if(Len-a[k-1].L-1>Max) { Max = Len - a[k-1].L-1; Index = a[k-1].L+1; } printf("%d %d\n", Max, Index); } return 0; } /* tstst 1 tst abcde 1 ac 3 1 5 0 */
时间: 2024-10-29 19:07:11