Boring counting HDU - 3518 suffix automata

Meaning of the questions:

For string S given length is 1000,

Seeking the number of essentially different substrings wherein these substrings meet appeared not to overlap at least twice in the string S

 

answer:

The string is then placed in a suffix automaton obtains substring corresponding to each node of the earliest and latest position of the string that appears subsuffix

Then according to

// return len [last] - len [fail [last]]; // add a plurality of different sub-sub-string of the string number produced 

and then change it in accordance with this
if (R[i] - L[i] > len[fail[i]]) ans += min(len[i], R[i] - L[i]) - len[fail[i]];

  1 #include <set>
  2 #include <map>
  3 #include <stack>
  4 #include <queue>
  5 #include <cmath>
  6 #include <ctime>
  7 #include <cstdio>
  8 #include <string>
  9 #include <vector>
 10 #include <cstring>
 11 #include <iostream>
 12 #include <algorithm>
 13 #include <unordered_map>
 14 
 15 #define  pi    acos(-1.0)
 16 #define  eps   1e-9
 17 #define  fi    first
 18 #define  se    second
 19 #define  rtl   rt<<1
 20 #define  rtr   rt<<1|1
 21 #define  bug                printf("******\n")
 22 #define  mem(a, b)          memset(a,b,sizeof(a))
 23 #define  name2str(x)        #x
 24 #define  fuck(x)            cout<<#x" = "<<x<<endl
 25 #define  sfi(a)             scanf("%d", &a)
 26 #define  sffi(a, b)         scanf("%d %d", &a, &b)
 27 #define  sfffi(a, b, c)     scanf("%d %d %d", &a, &b, &c)
 28 #define  sffffi(a, b, c, d) scanf("%d %d %d %d", &a, &b, &c, &d)
 29 #define  sfL(a)             scanf("%lld", &a)
 30 #define  sffL(a, b)         scanf("%lld %lld", &a, &b)
 31 #define  sfffL(a, b, c)     scanf("%lld %lld %lld", &a, &b, &c)
 32 #define  sffffL(a, b, c, d) scanf("%lld %lld %lld %lld", &a, &b, &c, &d)
 33 #define  sfs(a)             scanf("%s", a)
 34 #define  sffs(a, b)         scanf("%s %s", a, b)
 35 #define  sfffs(a, b, c)     scanf("%s %s %s", a, b, c)
 36 #define  sffffs(a, b, c, d) scanf("%s %s %s %s", a, b,c, d)
 37 #define  FIN                freopen("../in.txt","r",stdin)
 38 #define  gcd(a, b)          __gcd(a,b)
 39 #define  lowbit(x)          x&-x
 40 #define  IO                 iOS::sync_with_stdio(false)
 41 
 42 
 43 using namespace std;
 44 typedef long long LL;
 45 typedef unsigned long long ULL;
 46 const ULL seed = 13331;
47  const LL INFLL = 0x3f3f3f3f3f3f3f3fLL;
 48  const  int MAXN = 1E4 + 50 ;
 49  const  int MAXM = 8e6 + 10 ;
 50  const  int INF = 0x3f3f3f3f ;
 51 is  const  int MOD = 1E9 + . 7 ;
 52 is  
53 is  struct Suffix_Automaton {
 54 is      int Last, TOT, NXT [MAXN << . 1 ] [ 26 is ], Fail [MAXN << . 1 ]; // Last node is not the longest prefix for the character (the entire string) belongs to the number of added 
55     int len [MAXN << . 1 ]; // longest substring length (the number of sub-node string len = [X] - len [FA [X]]) 
56 is      LL NUM [MAXN << . 1 ]; // this state the number of sub-strings 
57 is      LL Maxx [MAXN << . 1 ]; // length sub-string x largest number of occurrences of substrings number 
58      LL SUM [MAXN << . 1 ]; // from behind the characters formed by the node the total number of strings 
59      LL subnum, sublen; // subnum represents a different number of strings, sublen string represents a different total length of 
60      int x-[MAXN << . 1 ], the Y [MAXN << . 1 ]; // the Y represents ranked as x node, X also represents the length of the preceding number 
61 is      int L [<< MAXN. 1 ], R [MAXN << . 1 ]; // L represents the earliest array corresponding to the node represents a position, R represents the position of the latest occurrence 
62 is  
63 is      void the init () {
 64          TOT = Last = . 1 ;
 65          Fail [ . 1 ] = len [ . 1 ] = 0 ;
 66          for ( int I = 0 ; I <= 25 ; I ++) NXT [ . 1 ] [I] = 0 ;
 67  
68      }
 69  
70      void Extend ( int C) {
 71 is          int U = + + tot, v = last;
 72         for (int i = 0; i <= 25; i++) nxt[u][i] = 0;
 73         fail[u] = 0;
 74         L[u] = R[u] = len[u] = len[v] + 1;
 75         num[u] = 1;
 76         for (; v && !nxt[v][c]; v = fail[v]) nxt[v][c] = u;
 77         if (!v) fail[u] = 1;
 78         else if (len[nxt[v][c]] == len[v] + 1) fail[u] = nxt[v][c];
 79         else {
 80             int now = ++tot, cur = nxt[v][c];
 81             len[now] = len[v] + 1;
 82             memcpy(nxt[now], nxt[cur], sizeof(nxt[cur]));
 83             fail[now] = fail[cur];
 84             fail[cur] = fail[u] = now;
 85             L[now] = L[cur], R[now] = R[cur];
 86             for (; v && nxt[v][c] == cur; v = fail[v]) nxt[v][c] = now;
 87         }
 88         last = u;
 89         //return len[last] - len[fail[last]];
90      }
 91 is  
92  
93      void get_sa () { // the Y expressed ranked node x, X also represents the length of the front of the number 
94          for ( int I = 0 ; I <= TOT; I ++) X-[I] = 0 ;
 95          for ( int I = . 1 ; I <= TOT; I ++) X-[len [I]] ++ ;
 96          for ( int I = . 1 ; I <= TOT; I ++) X-[I] + = X-[I - . 1 ];
 97          for ( int I = . 1 ; I <= TOT; I ++) the Y [X-[len [I]] -] = I;
 98      }
99  
100      int get_L_R () {
 101          int ANS = 0 ;
 102          for ( int I = TOT; I; i-- ) {
 103              L [Fail [the Y [I]]] = min (L [Fail [the Y [I] ]], L [the Y [I]]);
 104              R & lt [Fail [the Y [I]]] = max (R & lt [Fail [the Y [I]]], R & lt [the Y [I]]);
 105          }
 106          for ( int I = . 1 ; I <= TOT; I ++) // do not intersect and the number of sub-strings of at least 2 times appear 
107              IF (R & lt [I] - L [I]> len [Fail [I]]) + ANS min = (len [I], R & lt [I] - L [I]) - len [Fail [I]];
 108          return ANS;
109     }
110 } sam;
111 
112 char s[maxn];
113 
114 int main() {
115 #ifndef ONLINE_JUDGE
116     FIN;
117 #endif
118     while (~sfs(s)) {
119         if (s[0] == '#') break;
120         sam.init();
121         int len = strlen(s);
122         for (int i = 0; i < len; ++i) sam.extend((s[i] - 'a'));
123         sam.get_sa();
124         printf("%d\n", sam.get_L_R());
125     }
126 #ifndef ONLINE_JUDGE
127     cout << "Totle Time : " << (double) clock() / CLOCKS_PER_SEC << "s" << endl;
128 #endif
129     return 0;
130 }
View Code

 

Guess you like

Origin www.cnblogs.com/qldabiaoge/p/11574397.html