首页 > 其他分享 >【动态规划】子串、子序列问题

【动态规划】子串、子序列问题

时间:2023-07-06 15:01:58浏览次数:36  
标签:子串 cdots range 序列 长度 动态 dp 回文

目录

应用

应用1:Leetcode 647. 回文子串

题目

647. 回文子串

解题思路

动态规划

设 \(dp[i][j]\) 表示子串 \(s[i \cdots j]\) 是否是回文子串,若 \(dp[i][j] = True\),则表示子串 \(s[i \cdots j]\) 是回文子串,否则,它就不是回文子串。假设字符串 \(s\) 的长度为 \(n\)。

边界条件

当子串 \(s[i \cdots j]\) 长度为 \(1\) 时,它是一个回文子串,因此边界条件如下:

\[dp[i][i] = True, \ 0 \le i \le n - 1 \]

状态转移

对于字符串 \(s\),我们倒序遍历子串的起始位置 \(i\),同时使用指针 \(j\),从位置 \(i+1\) 开始顺序枚举子串 \(s[i \cdots j]\) 的结束位置

对于,任意一个子串 \(s[i \cdots j]\) ,存在两种情况,使得它是一个回文串:

  • 子串长度为 \(1\),即 \(i = j\);

  • 子串长度大于 \(1\),若 \(s[i] = s[j]\),且它的子串 \(s[i + 1 \cdots j - 1]\) 是一个回文串。

    这里需要注意,当子串长度为 \(2\) ,即\(j = i + 1\) 时,它的子串 \(s[i + 1 \cdots j - 1]\) 是一个空串 "",需要单独讨论。

否则,它就不是一个回文串。

因此,状态转移方程为:

\[dp[i][j] = \begin{cases} (s[i] == s[j]) \land (j - i <= 1 \lor dp[i + 1][j - 1]) , & i \lt j\\ False, & otherwise \end{cases} \]

这里,\(\land\) 表示逻辑与运算,\(\lor\) 表示逻辑或运算。

代码

class Solution:
    def countSubstrings(self, s: str) -> int:
        n = len(s)
        dp = [[False] * n for _ in range(n)]

        result = 0
        for i in range(n):
            dp[i][i] = True
            result += 1

        for i in range(n - 1, -1, -1):
            for j in range(i + 1, n):
                dp[i][j] = (s[i] == s[j]) and (j - i <= 1 or dp[i + 1][j - 1])
                if dp[i][j]:
                    result += 1
        return result

简化之后的代码如下:

class Solution:
    def countSubstrings(self, s: str) -> int:
        n = len(s)
        dp = [[False] * n for _ in range(n)]
        result = 0
        for i in range(n - 1, -1, -1):
            for j in range(i, n):
                if s[i] == s[j] and (j - i <= 1 or dp[i + 1][j - 1]):
                    result += 1
                    dp[i][j] = True
        return result

标签:子串,cdots,range,序列,长度,动态,dp,回文
From: https://www.cnblogs.com/larry1024/p/17532149.html

相关文章

  • Flask框架:运用Ajax轮询动态绘图
    Ajax是异步JavaScript和XML可用于前后端交互,在之前《Flask框架:运用Ajax实现数据交互》简单实现了前后端交互,本章将通过Ajax轮询获取后端的数据,前台使用echart绘图库进行图形的生成与展示,后台通过render_template方法返回一串JSON数据集,前台收到后将其应用到绘图库上,实现动态监控内......
  • scala case class和普通class 动态参数赋值
    普通class赋值,将A类的属性赋值给B类//动态赋值测试objectDynamicAssignmentTest{defmain(args:Array[String]):Unit={varaList=List(newA1("A1",12),newA1("A2",13),)valb1List=scala.collection.mutable.ListBuffer......
  • 动态库如何被加载
    linux的可执行文件都是ELF格式,它肯定是会有个section叫.interp,这里面保存的是动态链接器的路径。  我们在执行这个ELF格式的可执行文件时,内核会先根据.interp节找到动态链接器,然后把控制权交给动态链接器,由动态链接器去加载依赖的动态库。1、链接器如何找到依赖的动态库......
  • 22-数码管的动态显示
    1.数码管动态显示不同位的数码管显示不同的数值使用动态扫描的方式,使用6位8段数码管显示1,2,3,4,5,6,选中第一个数码管让其显示1,显示时间位T;经过时间T之后选中第二个数码管显示2,显示时间为T,依次进行相似的操作,显示到6之后,经过时间T之后再显示1显示一个周期所有的时间为6个周......
  • 学不会动态规划——背包篇
    前言终于把线性动态规划学完了,本蒟蒻要开始背包了,祝我好运吧!如果文章有任何问题,欢迎评论或者私信让我知道......
  • 「NOIP 模拟赛 20230705」T2-序列删数问题 题解
    题面Natsuzora有一个长度为\(n\)的排列\(a_1,a_2,\ldots,a_n\),他想要将序列中的\(m\)个数删除。删除数字需要使用到“魔法工具”,其也有\(m\)种,其中第\(i\)种魔法工具能够将排列中任意一个的长度为\(l_i\)的区间中最大的数删除。每个魔法工具最多只能使用\(1\)次。......
  • js如何动态清除form表单中input款下的错误信息
    form表单<formaction=""method="post"novalidateid="myform">{%csrf_token%}{%forforminform_obj%}<divclass="form-group"><labelfor="{{form.i......
  • Poi Excel 动态变化行高,动态创建Sheet
    需求Excel最终需要由A4纸打印出来标题名称需要动态变化行高自动变化每页都需要保留标题分析基础需求即填充标题填充数据,设置样式,基础需求可以通过easyExcel或者Poi的API来实现,但是由于需求3、4,easyExcel并不支持,只能选择使用ApachePoi。ApachePOI没有直接的API来自动......
  • 算法学习笔记( 一)(1)动态规划(LIS)
    题目链接:https://www.acwing.com/problem/content/897/讲解动态规划问题具有三个特质:子问题重叠:即子问题是相互之间依赖的这个子问题在之后可能被反复使用(此条件并非必要条件但失去它也就没有优化作用了)最优化原理:此问题可以通过子问题的代表元素(最优解)来求出这就......
  • 【Oracle】行转列的函数wm_concat,listagg,xmlagg,pivot以及动态行转列
    【Oracle】行转列的几种情况表的数据如下朴实无华的函数1.wm_concat使用格式:select分组字段,wm_concat(要转换的列名)from表名groupby分组字段实例:selectit.Code,wm_concat(it.inv)fromttt20230705itgroupbyit.Code2.listagg()withingroup()使用格式:......