POJ 3450 Corporate Identity

二分枚举+KMP

之前没注意字典序最小,WA了N次……

  1 #include <cstdio>
  2 #include <cstring>
  3 #include <cstdlib>
  4 #include <algorithm>
  5 
  6 using namespace std;
  7 
  8 const int MAXN = 4010;
  9 const int MAXL = 210;
 10 
 11 int N;
 12 char str[MAXN][MAXL];
 13 char temp[MAXL];
 14 char anser[MAXL];
 15 int nextval[MAXL];
 16 int len[MAXN];
 17 
 18 void GetNextVal( char *s, int lenth )
 19 {
 20     int i = 0, j = -1;
 21     nextval[0] = -1;
 22     while ( i < lenth )
 23     {
 24         if ( j == -1 || s[i] == s[j] )
 25         {
 26             ++i, ++j;
 27             if ( s[i] != s[j] ) nextval[i] = j;
 28             else nextval[i] = nextval[j];
 29         }
 30         else j = nextval[j];
 31     }
 32     return;
 33 }
 34 
 35 bool KMP( char *t, char *s, int lenth, int lenn )
 36 {
 37     GetNextVal( t, lenth );
 38     int i = 0, j = 0;
 39     while ( j < lenn )
 40     {
 41         if ( i == -1 || s[j] == t[i] )
 42         {
 43             ++i, ++j;
 44             if ( i == lenth ) return true;
 45         }
 46         else i = nextval[i];
 47         //if ( i == lenth ) return true;
 48     }
 49     return false;
 50 }
 51 
 52 bool check( int tpL )
 53 {
 54     bool flag = false;
 55     bool ok = false;
 56     for ( int st = 0; st + tpL - 1 < len[0]; ++st )
 57     {
 58         for ( int k = 0; k < tpL; ++k )
 59             temp[k] = str[0][ st + k ];
 60         temp[ tpL ] = '\0';
 61         //puts(temp);
 62 
 63         ok = true;
 64         for ( int i = 1; i < N; ++i )
 65             if ( !KMP( temp, str[i], tpL, len[i] ) )
 66             {
 67                 ok = false;
 68                 break;
 69             }
 70         if ( ok )
 71         {
 72             flag = true;
 73             if ( anser[0] == '\0' ||
 74                 ( strlen(anser) == strlen(temp) && strcmp( anser, temp ) > 0 ) || ( strlen(anser) < strlen(temp) ) )
 75                 strcpy( anser, temp );
 76         }
 77     }
 78     return flag;
 79 }
 80 
 81 int main()
 82 {
 83     while ( scanf( "%d", &N ), N )
 84     {
 85         int bound = 1 << 30;
 86         for ( int i = 0; i < N; ++i )
 87         {
 88             scanf( "%s", str[i] );
 89             len[i] = strlen( str[i] );
 90             bound = min( bound, len[i] );
 91         }
 92 
 93         int low = 0;
 94         int high = bound;
 95         int mid, ans = 0;
 96         anser[0] = '\0';
 97         while ( low <= high )
 98         {
 99             mid = ( low + high ) >> 1;
100             if ( check( mid ) )
101             {
102                 ans = mid;
103                 low = mid + 1;
104             }
105             else high = mid - 1;
106         }
107 
108         if ( !ans ) puts("IDENTITY LOST");
109         else puts(anser);
110     }
111     return 0;
112 }

 

posted @ 2013-05-25 20:34  冰鸮  阅读(174)  评论(0)    收藏  举报