classSolution { public: int dp[501]={0}; intmaxSumAfterPartitioning(vector<int>& A, int K){ int n = A.size(); for(int i = n-1; i>=0; --i) { int ma = 0; int j; for(j=i;j<i+K && j < n ;++j) { ma = max(ma, A[j]); dp[i] = max(dp[i], ma*(j - i + 1) + dp[j + 1]); } } return dp[0]; } };
namespace SA { boolcmp(int *r, int a, int b, int l) { return r[a] == r[b] && r[a + l] == r[b + l]; } voidda(int str[], int sa[], int rank[], int height[], int n, int m) { n++; int i, j, p, *x = t1, *y = t2; for (i = 0; i < m; i++) c[i] = 0; for (i = 0; i < n; i++) c[x[i] = str[i]]++; for (i = 1; i < m; i++) c[i] += c[i - 1]; for (i = n - 1; i >= 0; i--) sa[--c[x[i]]] = i; for (j = 1; j <= n; j <<= 1) { p = 0; for (i = n - j; i < n; i++) y[p++] = i; for (i = 0; i < n; i++) if (sa[i] >= j) y[p++] = sa[i] - j; for (i = 0; i < m; i++) c[i] = 0; for (i = 0; i < n; i++) c[x[y[i]]]++; for (i = 1; i < m; i++) c[i] += c[i - 1]; for (i = n - 1; i >= 0; i--) sa[--c[x[y[i]]]] = y[i]; swap(x, y); p = 1; x[sa[0]] = 0; for (i = 1; i < n; i++) x[sa[i]] = cmp(y, sa[i - 1], sa[i], j) ? p - 1 : p++; if (p >= n) break; m = p; } int k = 0; n--; for (i = 0; i <= n; i++) rank[sa[i]] = i; for (i = 0; i < n; i++) { if (k) k--; j = sa[rank[i] - 1]; while (str[i + k] == str[j + k]) k++; height[rank[i]] = k; } } int num_rank[MAXN], height[MAXN]; int num[MAXN]; int sa[MAXN]; } // namespace SA
classSolution { public: string longestDupSubstring(string S) { usingnamespace SA; int pos = 0; int len = 0; int n = S.length(); for (int i = 0; i <= n; ++i) { num[i] = S[i]&0x3f; } num[n] = 0; da(num, sa, num_rank, height, n, 256); for (int i = 2; i <= n; ++i) { if (height[i] > len) { pos = sa[i]; len = height[i]; } } return S.substr(pos, len); } };