最长回文子串、最长对称子串(同类型题)

L2-008 最长对称子串 - 团体程序设计天梯赛-练习集

最长回文子串--晴问算法

对给定的字符串,本题要求你输出最长对称子串的长度。例如,给定Is PAT&TAP symmetric?,最长对称子串为s PAT&TAP s,于是你应该输出11。

输入格式:

输入在一行中给出长度不超过1000的非空字符串。

输出格式:

在一行中输出最长对称子串的长度。

输入样例:

Is PAT&TAP symmetric?

输出样例:

11

题目描述

现有一个字符串s,求s的最长回文子串的长度。

输入描述

一个字符串s​​​​,仅由小写字母组成,长度不超过100

输出描述

输出一个整数,表示最长回文子串的长度。

样例1

输入

lozjujzve

输出

5

解释

最长公共子串为zjujz,长度为5

 题解(通用):动态规划

具体过程细节
  1. 初始化单个字符的回文状态:遍历字符串,将所有单个字符的回文状态设为 true
  2. 初始化长度为 2 的子串的回文状态:遍历字符串,检查相邻两个字符是否相同,如果相同则将对应的 dp[i][i+1] 设为 true,并更新 maxLength 为 2。
  3. 动态规划求解更长子串的回文状态:从长度为 3 的子串开始,逐步增加子串长度,直到整个字符串的长度。对于每个长度的子串,检查两端字符是否相同且去掉两端字符后的子串是否是回文子串,如果是,则更新 dp[i][j] 为 true,并更新 maxLength。
#include <bits/stdc++.h>
using namespace std;

const int MAXN = 1010;//开大于1000的,否则出错

int main()
{
   	string s;
   	getline(cin, s);
   	int n = s.size();
   	int maxLength = 1;
   	vector<vector<bool>> dp(MAXN,vector<bool>(MAXN, false));

    //bool dp[MAXN][MAXN];
    // 初始化单个字符的回文状态
   	for(int i=0;i<n;i++){
	   	dp[i][i] = true;
	}
	// 初始化长度为 2 的子串的回文状态
	for(int i=0;i<n-1;i++){
		if(s[i] == s[i+1]){
			dp[i][i+1] = true;
			maxLength = 2;
		}
	}
	for(int i=3;i<=n;i++){ //外层循环表示长度,从长度3开始遍历
		for(int j=0;j+i-1<n;j++){ 当长度为i时,从j开始的子串的末尾下标为j+i-1,要求不超过n 越界
			int k = j+i-1; //子串的尾下标
			if(s[j] == s[k] && dp[j+1][k-1]){ 
				dp[j][k] = true;
				maxLength = i;
			}
		}
	}
	cout<<maxLength;
	return 0;
}

题解二:

  • 使用双重循环遍历所有可能的子串。

  • 对于每个子串,调用 huiwen 函数判断是否是回文。

  • 如果是回文,则更新 maxLength

  • 时间复杂度:O(n3),其中 n 是字符串的长度。

#include <bits/stdc++.h>
using namespace std;

bool huiwen(string s){
	int len = s.size();
	for(int i=0;i<len/2;i++){
		if(s[i] != s[len-1-i]){
			return false;
		}
	}
	return true;
}

int main()
{
   	string s;
   	getline(cin, s);
   	int n = s.size();
   	int maxLength = 1;
   	for(int i=0;i<n;i++){
	   	for(int j=i+1;j<n;j++){
		   	string s1 = s.substr(i, j-i+1);
		   	if(huiwen(s1)){
		   		int len = s1.size();
			   	maxLength = max(maxLength, len);
			}
		}
	}
	cout<<maxLength;
	return 0;
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值