当前位置: 首页 > news >正文

[Algorithm][动态规划][回文串问题][回文子串][最长回文子串][分割回文串Ⅳ]详细讲解

目录

  • 0.原理讲解
  • 1.回文子串
    • 1.题目链接
    • 2.算法原理详解
    • 3.代码实现
  • 2.最长回文子串
    • 1.题目链接
    • 3.代码实现
  • 3.分割回文串 IV
    • 1.题目链接
    • 2.算法原理详解
    • 3.代码实现


0.原理讲解

  • 动态规划能够将所有的子串是否是回文的信息,保存在dp表里面
  • 状态表示一般经验:以[i, j]为区间,分析问题

1.回文子串

1.题目链接

  • 回文子串

2.算法原理详解

  • 思路
    • 确定状态表示 -> dp[i][j]的含义

      • s字符串[i, j]的子串,是否是回文串
    • 推导状态转移方程
      请添加图片描述

    • 初始化:无需初始化

    • 确定填表顺序:从下往上

    • 确定返回值:dp表里true的个数


3.代码实现

int countSubstrings(string s) 
{
    int n = s.size();
    vector<vector<bool>> dp(n, vector<bool>(n));

    int ret = 0;
    for(int i = n - 1; i >= 0; i--)
    {
        for(int j = i; j < n; j++)
        {
            if(s[i] == s[j])
            {
                dp[i][j] = i + 1 < j ? dp[i + 1][j - 1] : true;

                if(dp[i][j])
                {
                    ret++;
                }
            }
        }
    }

    return ret;
}

2.最长回文子串

1.题目链接

  • 最长回文子串

  • 按照回文子串的思路解决即可,只不过判断最长时,利用起始下标j - i + 1

  • 思路

    • 确定状态表示 -> dp[i][j]的含义

      • s字符串[i, j]的子串,是否是回文串
    • 推导状态转移方程
      请添加图片描述

    • 初始化:无需初始化

    • 确定填表顺序:从下往上

    • 确定返回值:dp表里值为true的情况下,长度最大的字串的起始位置以及长度


3.代码实现

string longestPalindrome(string s) 
{
    int n = s.size();
    vector<vector<bool>> dp(n, vector<bool>(n));

    int len = 1, begin = 0;
    for(int i = n - 1; i >= 0; i--)
    {
        for(int j = i; j < n; j++)
        {
            if(s[i] == s[j])
            {
                dp[i][j] = i + 1 < j ? dp[i + 1][j - 1] : true;

                if(dp[i][j] && j - i + 1 > len)
                {
                    len = j - i + 1;
                    begin = i;
                }
            }
        }
    }

    return s.substr(begin, len);
}

3.分割回文串 IV

1.题目链接

  • 分割回文串 IV

2.算法原理详解

  • 思路梳理

    • 本题思路经处理后,就可以划归为回文子串
    • 可以将本题分为三个区间,其中中间区间就是一个回文子串的始末
    • 先将字符串内所有子串是否是回文串都判断出来,再挨个判断三个区间是否是回文串
      请添加图片描述
  • 预处理:将字符串内所有子串是否是回文串都判断出来

    • 确定状态表示 -> dp[i][j]的含义

      • s字符串[i, j]的子串,是否是回文串
    • 推导状态转移方程
      请添加图片描述

    • 初始化:无需初始化

    • 确定填表顺序:从下往上

  • 结果处理:挨个判断三个区间是否是回文串


3.代码实现

bool checkPartitioning(string s) 
{
    // 预处理:处理回文信息
    int n = s.size();
    vector<vector<bool>> dp(n, vector<bool>(n));

    for(int i = n - 1; i >= 0; i--)
    {
        for(int j = i; j < n; j++)
        {
            if(s[i] == s[j])
            {
                dp[i][j] = i + 1 < j ? dp[i + 1][j - 1] : true;
            }
        }
    }

    // 判断三区间,枚举中间区间
    for(int i = 1; i < n - 1; i++)
    {
        for(int j = i; j < n - 1; j++)
        {
            if(dp[0][i - 1] && dp[i][j] && dp[j + 1][n - 1])
            {
                return true;
            }
        }
    }

    return false;
}

相关文章:

  • 深度解读CharGPT基本原理
  • PyTorch学习(12):PyTorch取极值(max, argmax, min, argmin)
  • 【JavaEE】Servlet
  • Google 解释AI 概览:关于上周的一些情况
  • (delphi11最新学习资料) Object Pascal 学习笔记---第14章泛型第2节(Object Pascal中的泛型)
  • 【2024年5月备考新增】】 考前篇(32)《必备资料(15) - 论文串讲-项目安全管理》
  • 大模型应用框架-LangChain
  • 计算机网络期末知识总结(第一章)
  • 【MyBatis】MyBatis操作数据库(二):动态SQL、#{}与${}的区别
  • 代码随想录-Day27
  • 【机器学习】探索未来科技的前沿:人工智能、机器学习与大模型
  • 学习小心意——python的构造方法和析构方法
  • 【图像处理与机器视觉】频率域滤波
  • YOLOv8+PyQt5海洋船只检测(可以重新训练,yolov8模型,从图像、视频和摄像头三种路径识别检测)
  • ESP使用巴法云远程OTA(VScode + Platform io)
  • Swoole 协程调度机制
  • 深度学习知识与心得
  • MFC工控项目实例之一主菜单制作
  • SEW交频器 MDX61801110-5A3-4-0T可议价
  • 手把手教你从0到1开发浏览器插件
  • 商务部:中方愿同各国一道加强合作,促进跨境电商健康可持续发展
  • 98岁动物学家、北京大学教授杨安峰逝世
  • 深入贯彻中央八项规定精神学习教育中央第七指导组指导督导中国船舶集团见面会召开
  • 同为“东部重要中心城市”后交出首份季报:宁杭苏表现如何?
  • 厦大历史系教授林汀水辞世,曾参编《中国历史地图集》
  • 解放军仪仗司礼大队仪仗分队参加纪念苏联伟大卫国战争胜利80周年阅兵活动