HDU-1711-Number Sequence(模式串匹配)

Posted angel-demon

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了HDU-1711-Number Sequence(模式串匹配)相关的知识,希望对你有一定的参考价值。

  • Rabin-Karp
    Accepted 1711 904MS 5272K 1310 B G++
    #include "bits/stdc++.h"
    using namespace std;
    typedef long long LL;
    const int MAXN = 1e6 + 5; 
    const int SEED = 1e9 + 7;
    int arr[MAXN];
    int main() {
        int t, n, m, k;
        scanf("%d", &t);
        while (t--) { 
            LL p = 0, s = 0, head = 1;
            bool flag = false;
            scanf("%d%d", &n, &m);
            for (int i = 1; i <= n; i++) {
                scanf("%d", &arr[i]);
            }
            // 获取模式串(M数组)的哈希值 
            for (int i = 1; i <= m; i++) {
                scanf("%d", &k); 
                head *= SEED;
                p = p * SEED + k;
            }
            // 获取arr[0]所表示的长度为m的串的哈希值 
            for (int i = 1; i < m; i++) {
                /*
                比较标准的写法是s = (s * SEED + arr[i]) % MOD;(MOD是一个和SEED互质的数)
                这里利用LL的溢出来省略MOD,可以将MOD看成2的64次方 
                */
                s = s * SEED + arr[i];
            } 
            for (int i = 1; i <= n - m + 1; i++) {
                // 用arr[i - 1]所表示的长度为m的串的哈希值得到arr[i]所表示的长度为m的串的哈希值  
                s = s * SEED - head * arr[i - 1] + arr[i + m - 1];
                if (s == p) {
                    flag = true;
                    printf("%d
    ", i);
                    break;
                }
            }
            if (!flag) {
                puts("-1");
            }
        }
        return 0;
    } 

    Rabin-Karp获取哈希值的形式有点像进制转换,由于计算机内二进制加减是不管符号的所以p和s变成负数也无所谓,用unsigned long long和long long是一样的。但是Rabin-Karp不保证匹配结果绝对正确,因为不同的串哈希值可能一样(long long的范围只有2的64次方,但是本题数组值的范围是[-1000000, 1000000],只要三四位产生的串的数量long long就不够放了)所以如果竞赛中用此法错了,可以尝试改SEED。还不行那就只能换方法了。

以上是关于HDU-1711-Number Sequence(模式串匹配)的主要内容,如果未能解决你的问题,请参考以下文章

hdu[1711]number sequence

hdu 1711 Number Sequence

HDU - 1711 Number Sequence

HDU 1711 Number Sequence(KMP模板)

hdu 1711 Number Sequence KMP模板题

HDU 1711 Number Sequence