题目:
给定一个字符串,找出不含有重复字符的最长子串的长度。
示例 1:
输入: "abcabcbb"
输出: 3
解释: 无重复字符的最长子串是 "abc",其长度为 3。
示例 2:
输入: "bbbbb"
输出: 1
解释: 无重复字符的最长子串是 "b",其长度为 1。
示例 3:
输入: "pwwkew"
输出: 3
解释: 无重复字符的最长子串是 "wke",其长度为 3。
请注意,答案必须是一个子串,"pwke" 是一个子序列 而不是子串。
第一想法:
java:
public static int lengthOfLongestSubstring(String s) {
//使用Set滑动方式进行子串的存储
Set<Character> set = new HashSet<>();
int lenth = s.length();
int ans=0, i = 0, j = 0;
while (i<lenth && j<lenth){
//当set中不存在当前字符时,将j位置的字符存入set,同时j向前一步继续比较
if (!set.contains(s.charAt(j))){
set.add(s.charAt(j++));
//取最长的子串距离
ans = Math.max(ans, j - i);
}
//存在时将尾部i位置的值移除,知道子串中不存在j位置相同的字符.
//**问题**:如果相同字符存在j-1的位置,那么就需要进行j-i次循环,可以考虑使用map记录位置,直接找到相同字符进行滑动.
else {
set.remove(s.charAt(i++));
}
}
return ans;
}
scala:
def LongestSubstring(s:String):Int = {
var res: Int = 0
val set = new mutable.HashSet[Char]
var head = 0
var foot = 0
val lenth = s.length
while (head<lenth && foot<lenth){
if (!set.contains(s.charAt(foot))){
set.add(s.charAt(foot))
foot+=1
res = math.max(res, foot-head)
}else {
set.remove(s.charAt(head))
head+=1
}
}
res
}
参考的优化方案:
public int lengthOfLongestSubstring(String s) {
int n = s.length(), ans = 0;
Map<Character, Integer> map = new HashMap<>(); // current index of character
// try to extend the range [i, j]
for (int j = 0, i = 0; j < n; j++) {
if (map.containsKey(s.charAt(j))) {
i = Math.max(map.get(s.charAt(j)), i);
}
ans = Math.max(ans, j - i + 1);
map.put(s.charAt(j), j + 1);
}
return ans;
}
def LongestSubstring2(s:String):Int = {
var res: Int = 0
val map:mutable.HashMap[Char,Int] = new mutable.HashMap[Char,Int]
var head = 0
var foot = 0
val lenth = s.length
while (foot<lenth ){
if (map.contains(s.charAt(foot))) {
head = math.max(map(s.charAt(foot)), head)
}
res = math.max(res, foot-head+1)
foot+=1
map.put(s.charAt(foot-1), foot)
}
res
}
**粗体** _斜体_ [链接](http://example.com) `代码` - 列表 > 引用
。你还可以使用@
来通知其他用户。