好题… 就是比平时的 hard 难了一些……

虽然猜出是数位DP了…不过比我之前做的题,好像多了一维,印象中都是一维记录之前状态就够了……然后就没做出……

至于 KMP 的应用更是神奇,虽然掌握的 kmp 但是真的想不到……

窝的代码能力太差了……总归是学到了……希望下次能做出来吧……

参考题解 https://leetcode-cn.com/problems/find-all-good-strings/solution/shu-wei-dp-kmp-by-qodjf/

国服现在好多大神…题解写的真的很棒~

cal 计算小于等于任意字符串 s 的数目,计算两次求差就可了。其中 s1 没有被计算,所以单独算一次即可。

dp[i][j][0]  前i个字符 和evil有j个相同 并且已经小于 S 证明后面的字符可以任意选择

dp[i][j][1]  前i个字符 和evil有j个相同 并且等于 S 的前 i 个字符 所以后面的字符必须小于等于 S

已知当前有 j 个字符和 evil 的前 j 个字符相等,下一个字符是 c ,则增加下一个字符之后有几个字符相等,这个就根据next数组的含义很容易计算。理解kmp应该都能懂。

以上。

class Solution {
public:
static const int mod = 1000000007;
int findGoodStrings(int n, string s1, string s2, string evil) {
int m = evil.size();
int nt[m + 1];
nt[0] = -1;
for (int j = 0, k = -1; j < m; ) {
if (k == -1 || evil[j] == evil[k]) nt[++j] = ++k;
else k = nt[k];
}
int f = s1.find(evil) == string::npos;
return (cal(n, s2, evil, nt) - cal(n, s1, evil, nt) + f + mod) % mod;
}
int cal(int n, string &s, string &evil, int nt[]) {
int m = evil.size();
int dp[n + 1][m][2];
// dp[i][j][0] 前i个字符 和evil有j个相同 0不和s相等 1和s相等
memset(dp, 0, sizeof dp);
dp[0][0][1] = 1;
for (int i = 0; i < n; i++) {
for (int j = 0; j < m; j++) {
for (char c = 'a'; c <= 'z'; c++) {
int len = getNextLen(evil, nt, j, c);
if (len < m) {
if (c < s[i]) {
up(dp[i+1][len][0], dp[i][j][1]);
}
if (c == s[i]) {
up(dp[i+1][len][1], dp[i][j][1]);
}
up(dp[i+1][len][0], dp[i][j][0]);
}
}
}
}
int ans = 0;
for (int i = 0; i < m; i++) {
up(ans, dp[n][i][0]);
up(ans, dp[n][i][1]);
}
return ans;
}
int getNextLen(string &evil, int nt[], int len, char c) {
while (len != -1 && evil[len] != c) len = nt[len];
return len + 1;
}
void up(int &x, int add) {
x = (x + add) % mod;
}
};

LeetCode 1397. Find All Good Strings 找到所有好字符串 (数位DP+KMP)的更多相关文章

  1. Leetcode 8. String to Integer (atoi) atoi函数实现 (字符串)

    Leetcode 8. String to Integer (atoi) atoi函数实现 (字符串) 题目描述 实现atoi函数,将一个字符串转化为数字 测试样例 Input: "42&q ...

  2. [LeetCode] 186. Reverse Words in a String II 翻转字符串中的单词 II

    Given an input string, reverse the string word by word. A word is defined as a sequence of non-space ...

  3. [LeetCode] 557. Reverse Words in a String III 翻转字符串中的单词 III

    Given a string, you need to reverse the order of characters in each word within a sentence while sti ...

  4. LeetCode 389. Find the Difference (找到不同)

    Given two strings s and t which consist of only lowercase letters. String t is generated by random s ...

  5. [LeetCode] 271. Encode and Decode Strings 加码解码字符串

    Design an algorithm to encode a list of strings to a string. The encoded string is then sent over th ...

  6. [LeetCode] Group Shifted Strings 群组偏移字符串

    Given a string, we can "shift" each of its letter to its successive letter, for example: & ...

  7. LeetCode 277. Find the Celebrity (找到明星)$

    Suppose you are at a party with n people (labeled from 0 to n - 1) and among them, there may exist o ...

  8. LeetCode 162. Find Peak Element (找到峰值)

    A peak element is an element that is greater than its neighbors. Given an input array where num[i] ≠ ...

  9. [LeetCode] Delete Operation for Two Strings 两个字符串的删除操作

    Given two words word1 and word2, find the minimum number of steps required to make word1 and word2 t ...

  10. LeetCode 41 First Missing Positive(找到数组中第一个丢失的正数)

    题目链接: https://leetcode.com/problems/first-missing-positive/?tab=Description   给出一个未排序的数组,求出第一个丢失的正数. ...

随机推荐

  1. 涨见识了!脱离vue项目竟然也可以使用响应式API

    前言 vue3的响应式API大家应该都特别熟悉,比如ref.watch.watchEffect等.平时大家都是在vue-cli或者vite创建的vue项目里面使用的这些响应式API,今天欧阳给大家带来 ...

  2. Git的分支管理和标签操作

    分支操作 分支是Git使用过程中非常重要的概念.使用分支意味着你可以把你的工作从开发主线上分离出来,以免影响开发主线. 同意一个仓库可以有多个分支,各个分支相互独立,互不干扰.通过git init 命 ...

  3. Continue-AI编程助手本地部署llama3.1+deepseek-coder-v2

    领先的开源人工智能代码助手.您可以连接任何模型和任何上下文,以在 IDE 内构建自定义自动完成和聊天体验 推荐以下开源模型: 聊天:llama3.1-8B 推理代码:deepseek-coder-v2 ...

  4. 【转载】 传统PID算法解决不了的情况,应该怎么办?

    原文地址: http://www.51hei.com/bbs/dpj-152844-1.html --------------------------------------------------- ...

  5. 始智AI —— https://wisemodel.cn/ —— 试用

    清华大学的合资企业推出的服务: 始智AI -- https://wisemodel.cn/ 链接: 始智AI -- https://wisemodel.cn/ 和modelscope比相对简约,毕竟功 ...

  6. (续)MindSpore计算框架如何发布训练好的模型到官方模型仓库MindSpore_Hub上 —— 对fork的MindSpore_Hub进行PR提交

    参考: https://gitee.com/mindspore/mindspore/blob/r1.2/CONTRIBUTING.md ================================ ...

  7. http与https通俗易懂的原理解析

    1.背景 经常都在说http.https,都知道https是安全的, 但是, 为什么说http不安全呢? 为什么又说https是安全的呢? 接下来我将使用通俗易懂的方式给大家分析一下....... 2 ...

  8. Salesforce Sales Cloud 零基础学习(五) My Labels的使用

    本篇参考: https://help.salesforce.com/s/articleView?id=sf.sales_core_record_labels.htm&type=5 在公司中,S ...

  9. k8s pvc扩容

    #查看是否支持扩容 $ kubectl get sc ** -o yaml ··· allowVolumeExpansion: true #拥有该字段表示允许动态扩容 ··· #找到需要扩容的pvc ...

  10. 关于对 Tomcat 进行小版本升级的快速解决方案

    1.背景描述 原来的 Tomcat 在部署时,使用的是最新的版本 9.0.40 . 经过一段时间后,在原来的 Tomcat 版本中,发现存在漏洞. 因此,需要将旧版本(9.0.40)升级到没有漏洞的新 ...