力扣(LeetCode) 5.最长回文子串

给定一个字符串 s,找到 s 中最长的回文子串。你可以假设 s 的最大长度为 1000。

示例 1:

输入: “babad”
输出: “bab”
注意: “aba” 也是一个有效答案。
示例 2:

输入: “cbbd”
输出: “bb”

来源:力扣(LeetCode)
链接:https://leetcode-cn.com/problems/longest-palindromic-substring
著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。

解法1:暴力法

例子:“babad”
在这里插入图片描述
判断每个子串是否是回文,然后找到其中最长的回文子串就可以了。
代码:

class Solution {
	bool Is_Palindrome(const string& str)
	{
		int left = 0;
		int right = str.size() - 1;
		while (left < right)
		{
			if (str[left] != str[right])
				return false;
			++left;
			--right;
		}
		return true;
	}
public:
	string longestPalindrome(string s)
	{
		string ret;
		for (int i = 0; i < (int)s.size(); i++)
		{
			if (ret.size() >= (s.size() - i))
				break;
			for (int j = s.size(); j > i; j--)
			{
				string str = s.substr(i, j - i);
				if (str.size() <= ret.size())
					break;
				if (Is_Palindrome(str) && str.size() > ret.size())
				{
					ret = str;
					break;
				}
			}
		}
		return ret;
	}
};

在牛客网上能跑过去,在leetcode上跑了70多用例,还要有30多用例跑不过(还特意加了几个break都不行),时间复杂度太大了可能。

解法2:动态规划

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
注意:"aa"这样的字符串在判断时,条件必须有buf[i] == buf[j] && i+1 == j;
因为在初始化的时候,所有的位置都是false,如果没有这个条件,
那么在判断完buf[i]==buf[j]时,再去判断buf[i+1] [j-1](也就是S[i,j]的子串 S[i+1,j-1])时,buf[i+1] [j-1]为false,条件不成立。
在这里插入图片描述
所以用buf[i] == buf[j] && i+1 == j;这个条件去判断。
当然,也可以在初始化的时候状态全部初始化为true。

代码:

class Solution {
public:
	string longestPalindrome(string s)
	{
		vector<vector<bool>> buf(s.size(), 
				vector<bool>(s.size(), false));
		for (int i = 0; i < (int)s.size(); i++)
			buf[i][i] = true;
		string ret;
		ret.push_back(s[0]);
		for (int i = s.size() - 2; i >= 0; i--)
		{
			for (int j = i + 1; j < (int)s.size(); j++)
			{
				if ((s[i] == s[j] && buf[i + 1][j - 1])||
					(s[i] == s[j] && i+1==j))
				{
					buf[i][j] = true;
					if (j - i + 1 > (int)ret.size())
						ret = s.substr(i, j - i + 1);
				}
			}
		}
		return ret;
	}
};
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值