标签:problem logs 包括 长度 size hash esc new .com
题目链接:https://leetcode.com/problems/longest-substring-without-repeating-characters/description/
题目大意:找出一串字符串的无重复子串。例子如下:
法一:两层for循环,一个字符一个字符的遍历其后是否有子串,且要判断是否不重复。这里有几个细节点,map的使用判断是否有重复,string.charAt(index)的使用摘出某一个字符。代码如下(耗时206ms):
1 public int lengthOfLongestSubstring(String s) { 2 int length = 1; 3 int max = 0; 4 for(int i = 0; i < s.length(); i++) { 5 length = 1; 6 Map<Character, Integer> map = new HashMap<Character, Integer>(); 7 map.put(s.charAt(i), i); 8 for(int j = i + 1; j < s.length(); j++) { 9 if(map.containsKey(s.charAt(j)) == false) { 10 //如果前面的字符串中没有当前字符,则将当前字符加入字符串中 11 length++; 12 map.put(s.charAt(j), j); 13 } 14 else { 15 //如果有,则直接退出从当前字符串起始位置的下一个位置开始重新计算字符串 16 //这里就有优化的地方了 17 break; 18 } 19 } 20 if(length > max) { 21 max = length; 22 } 23 } 24 return max; 25 }
法二(借鉴):一层for循环,用left记录子串起始位置,用set判断是否有重复,每走到下一个下标位置,判断当前存的子串中有没有当前字符,如果有,则根据left++将重复字符前面的包括它自己都从set中删去,也就是将重复字符+1作为新的子串的起始位置;如果没有,则将当前字符加入子串中。有点kmp的思想,这样只需要一次for循环即可。代码如下(耗时70ms):
1 public int lengthOfLongestSubstring(String s) { 2 int length = s.length(); 3 int left = 0, right = 0, ans = 0;//left记录子串开始下标,right记录子串结束下标 4 HashSet<Character> set = new HashSet<Character>();//set判断重复字符 5 while(right < length) { 6 if(set.contains(s.charAt(right)) == false) { 7 //前面的字符串中不包含当前字符 8 //将当前字符加入子串中,长度+1 9 set.add(s.charAt(right++)); 10 ans = Math.max(ans, set.size()); 11 } 12 else { 13 //前面的字符串中包含当前字符 14 //将重复字符前面的包括它自己都删去,也就是从重复字符+1开始重新计算子串 15 set.remove(s.charAt(left++)); 16 } 17 } 18 return ans; 19 }
还有别的方法,还没太看懂https://leetcode.com/problems/longest-substring-without-repeating-characters/solution/
3.Longest Substring Without Repeating Characters
标签:problem logs 包括 长度 size hash esc new .com
原文地址:http://www.cnblogs.com/cing/p/7824981.html