ICode9

精准搜索请尝试: 精确搜索
首页 > 其他分享> 文章详细

求n个数组(字符串)的最长公共子串

2021-07-04 21:58:56  阅读:121  来源: 互联网

标签:子串 paths cnt int mid 数组 字符串 长度


给定n个数组,求这n个数组的最长公共子串的长度,例如:

paths = [[0,1,2,3,4], [2,3,4], [4,0,1,2,3]]

的最长公共子串为[2,3],长度为2。
这类问题可以使用字符串hash来解决,首先是二分最长公共子串的长度。对于每个二分的长度,都去check是否存在该长度下的解。hash的主要目的是在O(1)时间得到每个数组的每个子串的hash值,这样就可以判断在相同长度下是否存在某个hash值在每个数组中都存在,即包含相同长度的子串。

typedef unsigned long long ULL;
const int N = 100010, P = 13771;
ULL h[N], p[N];

ULL get(int l, int r){
    return h[r] - h[l - 1] * p[r - l + 1];
}
class Solution {
public:
    vector<vector<int>> paths;
    unordered_map<ULL, int> mp, vis;
    bool check(int mid){
        mp.clear();
        for(int k = 0; k < paths.size(); k ++ ){
            auto &a = paths[k];
            p[0] = 1;
            for(int i = 1; i <= a.size(); i ++ ){
                h[i] = h[i - 1] * P + a[i - 1];
                p[i] = p[i - 1] * P;
            }
            vis.clear();
            for(int i = mid; i <= a.size(); i ++ ){
                ULL t = get(i - mid + 1, i);
                if(vis.count(t) == 0) {
                    mp[t] ++ ;
                    vis[t] = 1;
                }
            }
        }
        int cnt = 0;
        for(auto &[u, v]: mp) cnt = max(cnt, v);
        return cnt == paths.size();
    }
    int longestCommonSubpath(vector<vector<int>>& _paths) {
        paths = _paths;
        int l = 0, r = N;
        for(auto &path: paths) r = min(r, (int)path.size());
        while(l < r){
            int mid = l + r + 1 >> 1;
            if(check(mid)) l = mid;
            else r = mid - 1;
        }
        return l;
    }
};

Note:哈希函数的P可以调节以避免哈希冲突,一般调节顺序为131->1331->13331->133331

标签:子串,paths,cnt,int,mid,数组,字符串,长度
来源: https://blog.csdn.net/qq_40438165/article/details/118468092

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有