用三重循环求一个字符串的最大回文串(连续重复出现的最长子串)

字符串的最大回文串是指在字符串中连续重复出现的最长子串,如"jkjkfgsfgsfgsf",回文串有"jk":2,"fgs":3,"gsf":3,"sfg":2。(格式为 子串:出现次数)。

求回文串的基本思路是:从首字符开始取长度为2的子串"jk",然后取该子串后相邻的长度为2的子串"jk",两个子串相邻且相等,所以"jk"为该字符串的一个回文串,继续取之后的一个长度为2的子串"fg",与之前的子串不相等,则不再往下遍历,重新从首字符开始取长度为3的子串,依次类推,可以取长度为4,5,6,7的子串,不能取长度为8的子串,因为剩余的子串长度为6,不可能和长度为8的子串相等。这样一次循环结束后,从第二个字符开始取长度为2的子串,依次类推...

代码如下:

 

#include <string>
#include <iostream>
#include <cassert>
#include <algorithm>
#include <vector>
#include <map>
using namespace std;

typedef pair<string, int> PairStrInt;
class MyComp
{
public:
	bool operator()(const PairStrInt& lh, const PairStrInt& rh)const
	{
		//按string长度比较,长度一样,按int大小比较
		if(lh.first.length() == rh.first.length())
			if(lh.second == rh.second)
				return lh.first > rh.first;
			else
				return lh.second > rh.second;
		else
			return lh.first.length() > rh.first.length();
	}
};

bool GetMaxRepeateSubstr(const string& str, string& strResult)
{
	if(str.length() < 4) return false;

	map<string, int> mapResult;

	int nBegin = 0;
	int nEnd = str.length() - 4;
	for(; nBegin <= nEnd; ++nBegin)
	{
		int nSubLen = 2;
		int nMaxLen = (str.length() - nBegin) / 2;
		for(; nSubLen <= nMaxLen; ++nSubLen)
		{
			string strSub = str.substr(nBegin, nSubLen);
			int nNextBegin = nBegin;
			int nCount = 1;
			while(nNextBegin + nSubLen + nSubLen < str.length())
			{
				string strS = str.substr(nNextBegin + nSubLen, nSubLen);
				if(strSub == strS)
				{
					nNextBegin += nSubLen;
					++nCount;
				}
				else
					break;
			}

			if(nCount > 1)
			{
				map<string, int>::iterator iter = mapResult.find(strSub);
				if(iter != mapResult.end())
					iter->second = nCount;
				else
					mapResult.insert(make_pair<string, int>(strSub, nCount));
			}
		}
	}

	bool bGet = false;//mapResult中保存着所有的回文串,可以根据需求从map中取自己所需要的回文串
	if(!mapResult.empty())
	{
		vector<PairStrInt> v(mapResult.begin(), mapResult.end());
		strResult = v[0].second;
		bGet = true;
	}

	return bGet;
}

int main()
{
	string str("jkjkfgsfgsfgsf");
	string strResult;
	bool bGet = GetMaxRepeateSubstr(str, strResult);
	if(bGet)
		cout<<strResult<<endl;
	else
		cout<<"do not get result"<<endl;

	return 0;
}


这里只通过基本的循环完成需求,可能有其他算法,可以更快的计算出结果。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值