码迷,mamicode.com
首页 > 其他好文 > 详细

uva 11557 - Code Theft(KMP)

时间:2014-09-04 23:44:50      阅读:321      评论:0      收藏:0      [点我收藏+]

标签:style   http   color   os   io   ar   for   sp   on   

题目链接:uva 11557 - Code Theft

题目大意:给定n个文本,每个文本有一个文本名,现在给出一个文本,求给定文本和n个文本中连续相同行数最大值,并且输出文本名,注意为0时不用输出其它的文本名。

解题思路:将每个字符串用映射成一个hash值,然后对匹配文本枚举后缀,建立失配数组进行KMP匹配,记录下每个文本的匹配最大值。

#include <cstdio>
#include <cstring>
#include <map>
#include <string>
#include <iostream>
#include <algorithm>

using namespace std;
const int maxn = 105;
const int maxm = 10005;

int N, sz, len[maxn];
int s[maxn][maxm], jump[maxm];

char word[maxm];
string name[maxn];
map<string, int> g;

inline bool check (char ch) {
    return ch == ‘ ‘;
}

int get_id() {
    string str = "";
    int n = strlen(word);
    while (n && check(word[n-1]))
        n--;

    for (int i = 0; i < n; i++) {
        if (check(word[i]) && (i == 0 || check(word[i-1])))
            continue;
        str += word[i];
    }

    if (str == "")
        return 0;

    if (g.count(str))
        return g[str];

    return g[str] = sz++;
}

void get_jump (int n, int* a) {
    int p = jump[0] = jump[1] = 0;

    for (int i = 2; i <= n; i++) {
        while (p && a[p+1] != a[i])
            p = jump[p];

        if (a[p+1] == a[i])
            p++;
        jump[i] = p;
    }
}

int find (int* a, int n, int* b, int m) {

    int p = 0, ret = 0;
    for (int i = 1; i <= n; i++) {
        while (p && b[p+1] != a[i])
            p = jump[p];

        if (b[p+1] == a[i])
            p++;

        if (p >= m)
            return m;
        ret = max(ret, p);
    }
    return ret;
}

void init () {
    sz = 1;
    g.clear();
    memset(s, 0, sizeof(s));

    getchar();
    for (int i = 0; i <= N; i++) {
        if (i != N) {
            gets(word);
            name[i] = word;
        }

        int n = 0;
        while (gets(word) && strcmp(word, "***END***")) {
            int k = get_id();
            if (k == 0)
                continue;
            s[i][++n] = k;
        }

        len[i] = n;
    }

    /*
    for (int i = 0; i <= N; i++) {
        for (int j = 1; j <= len[i]; j++)
            printf("%d ", s[i][j]);
        printf("\n");
    }
    */
}

void solve () {
    int ans = 0, rec[maxn];
    memset(rec, 0, sizeof(rec));

    for (int k = 0; k <= len[N]; k++) {

        get_jump(len[N] - k, s[N]);
        for (int i = 0; i < N; i++)
            rec[i] = max(rec[i], find(s[i], len[i], s[N], len[N] - k));

        for (int i = 1; i < len[N] - k; i++)
            s[N][i] = s[N][i+1];
    }

    for (int i = 0; i < N; i++)
        ans = max(ans, rec[i]);

    cout << ans;

    if (ans) {
        for (int i = 0; i < N; i++)
            if (rec[i] == ans)
                cout << " " << name[i];
    }
    cout << endl;
}

int main () {
    while (cin >> N) {
        init();
        solve();
    }
    return 0;
}

uva 11557 - Code Theft(KMP)

标签:style   http   color   os   io   ar   for   sp   on   

原文地址:http://blog.csdn.net/keshuai19940722/article/details/39061223

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!