string - KMP前缀表

标签 string algorithm data-structures pattern-matching

我正在阅读关于 KMP 的字符串匹配。
它需要通过构建前缀表来对模式进行预处理。
例如,对于字符串 ababaca,前缀表是:P = [0, 0, 1, 2, 3, 0, 1]
但我不清楚这些数字说明了什么。我读到它有助于在模式移动时找到模式的匹配项,但我无法将此信息与表中的数字联系起来。

最佳答案

每个数字都属于相应的前缀(“a”、“ab”、“aba”、...),对于每个前缀,它代表与前缀匹配的字符串的最长后缀的长度。我们这里不把整个字符串算作后缀或前缀,它被称为自后缀和自前缀(至少在俄语中,不确定英语术语)。

所以我们有字符串“ababaca”。我们来看看吧。 KMP 为每个非空前缀计算前缀函数。让我们将 s[i] 定义为字符串,将 p[i] 定义为 Prefix 函数。前缀和后缀可以重叠。

+---+----------+-------+------------------------+
| i |  s[0:i]  | p[i]  | Matching Prefix/Suffix |
+---+----------+-------+------------------------+
| 0 | a        |     0 |                        |
| 1 | ab       |     0 |                        |
| 2 | aba      |     1 | a                      |
| 3 | abab     |     2 | ab                     |
| 4 | ababa    |     3 | aba                    |
| 5 | ababac   |     0 |                        |
| 6 | ababaca  |     1 | a                      |
|   |          |       |                        |
+---+----------+-------+------------------------+

计算字符串 S 前缀函数的简单 C++ 代码:

vector<int> prefixFunction(string s) {
    vector<int> p(s.size());
    int j = 0;
    for (int i = 1; i < (int)s.size(); i++) {
        while (j > 0 && s[j] != s[i])
            j = p[j-1];

        if (s[j] == s[i])
            j++;
        p[i] = j;
    }   
    return p;
}

关于string - KMP前缀表,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/13792118/

相关文章:

javascript - 为什么我的话被切成两半?

c - 在c中将子字符串插入到另一个字符串中

Java Date/Calendar 对象字符串,比较

algorithm - 最好的压缩算法? (最佳定义见下文)

c++ - 打印通过标准输入输入的整个字符串

c++ - 键/值数组的双调排序

algorithm - 使用什么算法来格式化 EDIFACT 文件?

java - 列为 Java 中 hashMap 的值

数据结构可以包含多种类型的元素吗?

algorithm - 构建四叉树,使得相邻节点之间只有一级差异 (LOD)