求最長公共子串的長度程式碼
阿新 • • 發佈:2019-01-05
#include<iostream> #include<string> #include<vector> using namespace std; string str1, str2; typedef long long ll; const ll maxn = 1000; const ll MOD = 1000000007; const ll P = 10000019; vector<pair<int, int>> pr1, pr2; ll H1[maxn], H2[maxn]; ll powp[maxn]; void init(int len) { // 為了得到powp陣列,省去後面操作的時間 powp[0] = 1; for(int i = 1; i <= len; i++) { powp[i] = (powp[i-1] * P)%MOD; } } void calH(ll H[], string str) { //計算每個字串的雜湊值 H[0] = str[0]; for(int i = 1; i < str.length(); i++) { H[i] = (H[i-1] * P + str[i]) % MOD; } } int calsinglesubH(ll H[], int i, int j) { if(i == 0) return H[j]; else return ((H[j] - H[i-1]*powp[j-i+1]) % MOD + MOD) % MOD; } void calsubH(ll H[], int len, vector<pair<int, int>> &pr) { //計算每個字串單個子串的雜湊值,並用vector儲存 for(int i = 0; i < len; i++) { for(int j = 0; j < len; j++) { int hashvalue = calsinglesubH(H, i, j); pr.push_back(make_pair(hashvalue, j-i+1)); } } } int getmax() { //計算兩個字串最長相同子串的長度 int ans = 0; for(int i = 0; i < pr1.size(); i++) { for(int j = 0; j < pr2.size(); j++) { if(pr1[i].first == pr2[j].first) { ans = max(ans, pr1[i].second); } } } return ans; } int main() { getline(cin, str1); getline(cin, str2); init(max(str1.length(), str2.length())); calH(H1, str1); calH(H2, str2); calsubH(H1, str1.length(), pr1); calsubH(H2, str2.length(), pr2); printf("ans = %d", getmax()); return 0; }
測試用例:
ILOVEYOU
YOUDONTLOVEME
執行結果:
ans = 4
具體分析步驟有空再補,程式碼先看著