Disubstr-distinct substringsNo Tags
Given A string, we need to find the total number of its distinct substrings.
Input
T-number of test cases. t<=20;
Each test case consists of one string, whose length is <= 1000
Output
For all test case output one number saying the number of distinct substrings.
Example
Sample Input:
2
Ccccc
Ababa
Sample Output:
5
9
Explanation for the TestCase with string Ababa:
Len=1:a,b
Len=2:ab,ba
Len=3:aba,bab
Len=4:abab,baba
Len=5:ababa
Thus, total number of distinct substrings is 9.
Submit solution!
Title Link: Spoj disubstr
Initially want to use a dictionary tree, the result of static build Trie timeout (lazy write dynamic pointer version ...) The truth is done with a suffix array, because each suffix contributes originally to its length, originally total contribution to $ (len + 1) * len/2$, but due to some string repetition, we want to subtract, and then think again, these are the prefixes of suffixes, namely $suffix (x) $ and $suffix (y) $ The public prefix $LCP (x, y) $, but how does x and y determine to accurately and not omit these repeated strings? Sorted by dictionary, and then the height array is a dictionary-ordered suffix, so it's good to lose all the height values. However, it seems that someone with a pointer to write the trie over, sure enough pointers in addition to the risk of exploding memory, the speed is really fast ah.
Think about it with a suffix array as long as $o (Nlog_{2}n) $, while the dictionary tree at least $o (n*n) $, is really not a grade ...
Code:
#include <stdio.h> #include <iostream> #include <algorithm> #include <cstdlib> #include < cstring> #include <bitset> #include <string> #include <stack> #include <cmath> #include < queue> #include <set> #include <map>using namespace std; #define INF 0x3f3f3f3f#define LC (x) (x<<1) # Define RC (x) ((x<<1) +1) #define MID (y x) ((x+y) >>1) #define FIN (name) freopen (name, "R", stdin) #define FOUT ( Name) freopen (name, "W", stdout) #define CLR (Arr,val) memset (arr,val,sizeof (arr)) #define FAST_IO Ios::sync_with_stdio ( FALSE); Cin.tie (0); typedef pair<int, int> pii;typedef long long ll;const double PI = ACOs ( -1.0); const int N = 1010;in T wa[n], Wb[n], cnt[n], Sa[n];int ran[n], height[n];char s[n];inline int cmp (int r[], int A, int b, int d) {return r[a] = = R[b] && r[a + d] = = R[b + d];} void DA (int n, int m) {int i; int *x = WA, *y = WB; for (i = 0; i < m; ++i) cnt[i] = 0; for (i = 0; i < n; ++i) ++cnt[x[i] = s[i]]; for (i = 1; i < m; ++i) cnt[i] + = cnt[i-1]; for (i = n-1; I >= 0; i.) sa[--cnt[x[i]] [i]; for (int k = 1; k <= N; k <<= 1) {int p = 0; for (i = n-k; i < n; ++i) y[p++] = i; for (i = 0; i < n; ++i) if (Sa[i] >= k) y[p++] = sa[i]-K; for (i = 0; i < m; ++i) cnt[i] = 0; for (i = 0; i < n; ++i) ++cnt[x[y[i]]; for (i = 1; i < m; ++i) cnt[i] + = cnt[i-1]; for (i = n-1; I >= 0; i) sa[--cnt[x[y[i]]] [= Y[i]; Swap (x, y); X[sa[0]] = 0; p = 1; for (i = 1; i < n; ++i) x[sa[i]] = cmp (y, sa[i-1], sa[i], K)? P-1: p++; m = p; if (P >= N) break; }}void getght (int n) {int I, k = 0; for (i = 1; I <= n; ++i) ran[sa[i]] = i; for (i = 0; i < n; ++i) {if (k)--k; Int j = Sa[ran[i]-1]; while (S[i + K] = = S[j + K]) ++k; Height[ran[i]] = k; }}int Main (void) {int T, I; scanf ("%d", &t); while (t--) {scanf ("%s", s); int len = strlen (s); DA (len + 1, *max_element (s, S + len) + 1); Getght (len); int ans = (len + 1) * len >> 1; for (i = 1; I <= len; ++i) ans-= height[i]; printf ("%d\n", ans); } return 0;}
Spoj Distinct substrings (suffix array to find the number of different substrings, good questions)