DEV Community

Cover image for 一个字符串匹配多个字符串
IQIUM
IQIUM

Posted on • Edited on

3 2

一个字符串匹配多个字符串

题目来源:392. 判断子序列 - 力扣

这个假如有多个字符串需要判断是否是字符串的子串

对于给定字符串t,给定待匹配字符串数组words,字符串的一个子序列是原始字符串删除一些(也可以不删除)字符而不改变剩余字符相对位置形成的新字符串。(例如,"ace""abcde"的一个子序列,而"aec"不是)。

这里主要看它的进阶问题:

如果有大量输入的 S,称作 S1, S2, ... , Sk 其中 k >= 10亿,你需要依次检查它们是否为 T 的子序列。在这种情况下,你会怎样改变代码?

对于这样情况下,我们不可能考虑10亿个依次进行比较,这样的效率太低而且会超时,可以借鉴KMP的思想,提前记录下一个字符出现的地方

举个例子, 比如对于字符串' abc'(前面添加一个空格,方便后续处理),a 出现的地方在下标为 1 的地方,c 出现在下标为 3 的地方。

那么如果我们后面找字符串 'ac',索引的顺序就变成了 1->3,提高了访问效率。

我们可以给字符串(后面我们称为t)建立一个索引二维数组dp,t.length * 26(26个英文字母)

vector<vector<int>> dp(length, vector<int>(26, 0));
Enter fullscreen mode Exit fullscreen mode

对于每个字符,我们从后往前遍历,这样很方便记录下一个字符出现的地方:

for (int i = 0; i < 26; ++i) {
    int nextPos = -1;
    for (int j = length - 1; j >= 0; --j) {
        dp[j][i] = nextPos;
        if (('a' + i) == t[j]) {
            nextPos = j;
        }
    }
}
Enter fullscreen mode Exit fullscreen mode

这里dp[i][j] 代表的是当前字符距离下一个字符'a'+j 出现的位置

那么,对于我们待查找的字符串 s,只需要从index 开始查找,直到结束:

int index = 0;
for (char &ch : s) {
    index = dp[index][ch - 'a'];
    if (index == -1) {
        return false;
    }
}
return true;
Enter fullscreen mode Exit fullscreen mode

这里为什么要记录呢?因为查找字符是否出现在字符串中有很多方法,暴力遍历、位运算都是值得记录的。

AWS GenAI LIVE image

How is generative AI increasing efficiency?

Join AWS GenAI LIVE! to find out how gen AI is reshaping productivity, streamlining processes, and driving innovation.

Learn more

Top comments (0)

Billboard image

The Next Generation Developer Platform

Coherence is the first Platform-as-a-Service you can control. Unlike "black-box" platforms that are opinionated about the infra you can deploy, Coherence is powered by CNC, the open-source IaC framework, which offers limitless customization.

Learn more

👋 Kindness is contagious

Please leave a ❤️ or a friendly comment on this post if you found it helpful!

Okay