題目
給定一個字串,找出不含有重複字元的 最長子串 的長度。
示例:
-
給定 “abcabcbb” ,沒有重複字元的最長子串是 “abc” ,那麼長度就是3。
-
給定 “bbbbb” ,最長的子串就是 “b” ,長度是1。
-
給定 “pwwkew” ,最長子串是 “wke” ,長度是3。請注意答案必須是一個子串,”pwke” 是 子序列 而不是子串。
方案1
思路:
-
字元對應的數字作為下標
-
初始化一個255的boolean作為所有可能出現的字元對應的存在可能性,不存在重複的均為false,存在重複的,則對應的下標置為true。
-
兩個指標進行移動,前指標先不動,後指標移動並根據當前字元對應整數下標是否為false或者true進行判斷。如果是false,則表示沒有重複,則指標向後移動一位;如果為true,表示存在重複,則後指標停止移動,並計算當前字串長度,且將boolean陣列重置,第一個指標向前移動一位,後指標指向當前前指標。
class Solution {
public int lengthOfLongestSubstring(String s) {
int len = 0 ;
if (s==null || s.length()== 0 )
{
return 0;
}
if (s.length() == 1){
return 1;
}
int firstPoint = 0;
int nextPoint = 0;
boolean[] exist=new boolean[255];
while (nextPoint < s.length()&&firstPoint <s.length()){
int currMax = 0;
int index = s.charAt(nextPoint)-0;
while (exist[index] == false&&nextPoint<s.length()){
exist[s.charAt(nextPoint)-0] = true;
nextPoint++;
if (nextPoint < s.length()){
index = s.charAt(nextPoint)-0;
}
}
currMax = Math.max(currMax,nextPoint-firstPoint);
firstPoint++;
nextPoint=firstPoint;
len = Math.max(len,currMax);
for (int i = 0 ; i < 255 ; i++)
{
exist[i] = false;
}
}
return len;
}
}
複製程式碼
方案2
思路:
以一個hashmap作為輔助,map的key儲存的是字元,value儲存的是該字元當前的位置,首先設定一個頭指標,指向字串開頭,那麼從開始遍歷字串,如果map當中不包含這個字元,那麼用這個字元當前所在的位置減去頭指標的位置,然後與最大長度做比較,選打的成為最大長度,然後把當前字元的以及位置放入map,以abba為例,頭指標指向a,當前為a,那麼長度為1,map。put(‘a’,0),當前為b,那麼長度為2,map.put(`b`,1),如果說map中存在當前字元,那麼把頭指標指向,頭指標當前的位置與map中儲存該字元位置的下一個位置當中的較大者,成為新的頭指標位置,比如當走到第二個b的時候,那麼頭指標原來是0,當前map中存放b的位置是1,那麼頭指標指向2,所以長度為1,比最大長度小不進行替換,最後將當前的字元及位置放入map,現在是map.put(`b`,2),然後走到了a,那麼當前map中a的位置是0,那麼它的下一個位置是1,與當前頭指標位置2相比,小於當前頭指標的位置,那麼頭指標不跟新,所以長度為2,與最大長度相等,所以不替換,最後求出最大長度為2.
public static int lengthOfLongestSubstring(String s) {
Map<Character,Integer> map=new HashMap<Character,Integer>();
int maxLength=0;
int now=0;
for(int i=0;i<s.length();i++){
if(map.containsKey(s.charAt(i))){
now=Math.max(map.get(s.charAt(i))+1,now);
if((i-now+1)>maxLength){
maxLength=i-now+1;
}
}else{
if((i-now+1)>maxLength){
maxLength=i-now+1;
}
}
map.put(s.charAt(i), i);
}
return maxLength;
}
複製程式碼