leetCode—Longest Palindromic Substring
2015-08-07 22:04
405 查看
Description:Given a string S,
find the longest palindromic substring in S. You may assume that the maximum length of S is
1000, and there exists one unique longest palindromic substring.
问题描述:给出一个字符串,求出这个字符串的最大回文子字符串。
解法一:看到这个问题,我们首先很容易想出时间复杂度是O(n^2),空间复杂度为O(n^2)的动态规划方法
代码如下:
解法二:
那么,是不是有时间复杂度和空间复杂度的都是线性的解决方法了,答案是肯定的,那就是使用Manacher’s Algorithm,(我翻译为马努切尔算法)。算法的思想可以查看这篇博客(Manacher's
ALGORITHM)和Longest Palindromic Substring Part II,这个算法我从阅读思想到实现,我花了半天的时间,一开始根本看不懂,准备放弃,最后坚持看下去了,当自己写的代码通过的时候,心里还是很开心的。废话不多说了,直接给出我写的代码:
find the longest palindromic substring in S. You may assume that the maximum length of S is
1000, and there exists one unique longest palindromic substring.
问题描述:给出一个字符串,求出这个字符串的最大回文子字符串。
解法一:看到这个问题,我们首先很容易想出时间复杂度是O(n^2),空间复杂度为O(n^2)的动态规划方法
代码如下:
public String longestPalindrome(String s) { if(s==null||s.length()==0) return null; int n=s.length(); int longestBegin=0; int maxLen=1; boolean[][] table=new boolean ; for(int i=0;i<n;i++){ table[i][i]=true; } for(int i=0;i<n-1;i++){ if(s.charAt(i)==s.charAt(i+1)){ table[i][i+1]=true; longestBegin =i; maxLen=2; } } for(int i=n-3;i>=0;i--){ for(int j=i+1;j<n;j++){ if(s.charAt(i)==s.charAt(j)&&table[i+1][j-1]){ table[i][j]=true; if(maxLen<j-i+1){ longestBegin=i; maxLen=j-i+1; } } } } return s.substring(longestBegin,longestBegin+maxLen); }
解法二:
那么,是不是有时间复杂度和空间复杂度的都是线性的解决方法了,答案是肯定的,那就是使用Manacher’s Algorithm,(我翻译为马努切尔算法)。算法的思想可以查看这篇博客(Manacher's
ALGORITHM)和Longest Palindromic Substring Part II,这个算法我从阅读思想到实现,我花了半天的时间,一开始根本看不懂,准备放弃,最后坚持看下去了,当自己写的代码通过的时候,心里还是很开心的。废话不多说了,直接给出我写的代码:
public static String longestPalindrome(String s) { if(s==null||s.length()==0) return null; int[] arr=getP(s); int max=arr[0]; int center=0; for(int i=1;i<arr.length;i++){ if(arr[i]>max){ max=arr[i]; center=i; } } String res=null; int centerIndex=0; //这里面需要考虑这两种情况 if(center%2==0){ centerIndex=(center-2)/2; res=s.substring(centerIndex-(max-2)/2,centerIndex+(max-2)/2+1); } else{ centerIndex=(center-1)/2; res=s.substring(centerIndex-(max-1)/2, centerIndex+(max-1)/2); } return res; } /** * S $#1#2#2#1#2#3#2#1#^ * P 0121252141216121210 *这个函数就是求这里面的P数组 *(p.s. 可以看出,P[i]-1正好是原字符串中回文串的总长度) * */ public static int[] getP(String s){ String str=preprocess(s); int[] p=new int[str.length()]; int mx=0; int id=0; for(int i=1;i<str.length()-1;i++){ if(mx>i){ p[i]=Math.min(p[2*id-i], mx-i); } else p[i]=1; while(str.charAt(i+p[i])==str.charAt(i-p[i])) { p[i]++; } if(i+p[i]>mx){ mx=i+p[i]; id=i; } } return p; } /** *处理字符串,把字符串形如“12212321”转化成“$#1#2#2#1#2#3#2#1#^” *(1)在头尾加$和^字符串可以使我们不用考虑越界问题 *(2)在中间加#字符串是为了使字符串的长度为奇数,这样就不用分奇偶两种 *情况去考虑了,处理起来更加方便 **/ private static String preprocess(String str){ int length=str.length(); char[] ch=new char[2*length+3]; ch[0]='$'; for(int i=0;i<str.length();i++){ ch[2*i+1]='#'; ch[2*i+2]=str.charAt(i); } ch[2*length+1]='#'; ch[2*length+2]='^'; return String.valueOf(ch); }
相关文章推荐
- hive 实战笔记case4
- 明知道员工不喜欢干一件事,干不好一件事,你还一定要他去干,犯贱就贱在和员工讲道理争输赢,有意思吗?人尽其才,物尽其用(转)
- hdu5355 Cake(构造)
- 怎样在Powerpoint中剪裁视频或音频ppt背景素材
- 搭系统--第1天
- Ubuntu下制作ISO镜像的U盘启动盘方法
- 自定义java注解(二) 实现DBHelper中的getCon( )得到数据库连接
- POJ 3621(0/1分数规划,二分) Sightseeing Cows
- 爬虫登陆极客学院,并下载视频
- Swift学习笔记(二十一)——字典
- 解决vista和win7在windows服务中交互桌面权限问题:穿透Session 0 隔离
- 倒油问题之深搜和广搜算法
- 地图与定位
- 欢迎使用CSDN-markdown编辑器
- js如何截取以逗号隔开的字符串
- 图论-最短路问题
- win7 删除Windows服务的方法!
- HDU2.1.4 Cake
- hive 实战笔记case3
- 数论 - 线性筛法与积性函数