程序師世界是廣大編程愛好者互助、分享、學習的平台,程序師世界有你更精彩!
首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫知識
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
 程式師世界 >> 編程語言 >> C語言 >> C++ >> C++入門知識 >> UVA 11557 - Code Theft (KMP + HASH)

UVA 11557 - Code Theft (KMP + HASH)

編輯:C++入門知識

UVA 11557 - Code Theft (KMP + HASH)


UVA 11557 - Code Theft

題目鏈接

題意:給定一些代碼文本,然後在給定一個現有文本,找出這個現有文本和前面代碼文本,重復連續行最多的這些文本

思路:把每一行hash成一個值,然後對於每一個文本計算最大匹配值,枚舉後綴,然後利用KMP去找即可

代碼:

#include 
#include 
#include 
#include 
#include 
#include 
using namespace std;

typedef unsigned long long ull;

const ull X = 123;
const int N = 105;

int n, next[1000005];
string name[N];
string s;
vector ans;
vector code[N];

void hash(string s, int u) {
    string ss = "";
    int l = 0, r = s.length() - 1, len = s.length();;
    while (s[l] == ' ' && l < len) l++;
    while (s[r] == ' ' && r >= 0) r--;
    for (int i = l; i <= r; i++) {
	ss += s[i];
	while (s[i] == ' ' && s[i + 1] == ' ' && i < r) i++;
    }
    if (ss == "") return;
    ull ans = 0;
    for (int i = ss.length() - 1; i >= 0; i--)
	ans = ans * X + ss[i];
    code[u].push_back(ans);
}

void build(int i) {
    code[i].clear();
    while (getline(cin, s) && s != "***END***") {
	hash(s, i);
    }
}

vector T;

void getnext() {
    int N = T.size();
    next[0] = next[1] = 0;
    int j = 0;
    for (int i = 2 ; i <= N; i++) {
	while (j && T[i - 1] != T[j]) j = next[j];
	if (T[i - 1] == T[j]) j++;
	next[i] = j;
    }
}

int find() {
    int ans = 0;
    int N = code[n].size(), m = T.size(), j = 0;
    for (int i = 0; i < N; i++) {
	while (j && code[n][i] != T[j]) j = next[j];
	if (code[n][i] == T[j]) j++;
	ans = max(ans, j);
	if (j == m)
	    return m;
    }
    return ans;
}

int cal(int u) {
    int ans = 0;
    int sz1 = code[u].size();
    for (int i = 0; i < sz1; i++) {
	T.clear();
	for (int j = i; j < sz1; j++)
	    T.push_back(code[u][j]);
	getnext();
	ans = max(ans, find());
    }
    return ans;
}

void solve() {
    int Max = 0;
    ans.clear();
    for (int i = 0; i < n; i++) {
	int tmp = cal(i);
	if (tmp > Max) {
	    Max = tmp;
	    ans.clear();
	    ans.push_back(i);
	}
	else if (tmp == Max) ans.push_back(i);
    }
    cout << Max;
    if (Max) {
	for (int i = 0; i < ans.size(); i++)
	    cout << " " << name[ans[i]];
    }
    cout << endl;
}

int main() {
    while (cin >> n) {
	getchar();
	for (int i = 0; i < n; i++) {
	    getline(cin, name[i]);
	    build(i);
	}
	build(n);
	solve();
    }
    return 0;
}


  1. 上一頁:
  2. 下一頁:
Copyright © 程式師世界 All Rights Reserved