给定一个字符串 s ,请你找出其中不含有重复字符串的最长子串的长度。
输入: s = "abcabcbb"输出: 3解释: 因为无重复字符的最长子串是 "abc",所以其长度为 3。
解题思路
滑动窗口。分别初始化一个窗口左指针和右指针,先移动右指针,并把指针经过的字符储存起来(Set或者Map),下次移动右指针的时候进行检查是否有元素重复,如果有元素重复则开始移动左指针,并把左指针经过的元素从储存的数据结构中移除。在每次进行移除之后都进行左指针和右指针的差和result进行比较。
const lengthOfLongestSubstring = function(s) {
let left = right = 0
let result = 0
let window = {}
while(right<s.length){
let rightChar = s[right]
right++
if(window[rightChar]===undefined){
window[rightChar] = 1
}else{
window[rightChar]++
}
while(window[rightChar]>1){
let leftChar = s[left]
left++
window[leftChar]--
}
result = Math.max(result,right-left)
}
return result
}
Go
复习语法:初始化储存在Heap上的数据结构可以先试用 make 进行内存分配;go中没有max这种函数,要自己写;从 window[rightChar] 中取元素需要进行ok的判断;
func lengthOfLongestSubstring(s string) int {
window := make(map[byte]int)
left,right,result:=0,0,0
for right < len(s) {
rightChar := s[right]
right++
if _,ok := window[rightChar];!ok{
window[rightChar] = 1
}else{
window[rightChar]++
}
for window[rightChar] > 1 {
leftChar := s[left]
left++
window[leftChar]--
}
result = max(result,right-left)
}
return result
}
func max(a,b int) int {
if a>b {
return a
}
return b
}
Rust
复习语法:不能直接遍历String,需要先变成vec,s.chars().collect();max可以在int类型上直接调用;遍历vec需要调用iter,enumerate和for_each;HashSet的方法contain查看是否包含某元素,remove删除元素;HashMap的方法remove也是删除元素。
use std::collections::HashMap;
impl Solution {
pub fn length_of_longest_substring(s: String) -> i32 {
let (mut result, mut current) = (0, 0);
let mut window = HashMap::new();
let mut s = s.chars().collect::<Vec<_>>();
let mut left = 0;
s.iter().enumerate().for_each(|(i, cha)| {
match window.get(cha) {
None => {
current += 1;
result = result.max(current);
}
Some(&i) => {
for c in &s[left..=i] {
window.remove(c);
}
current -= i - left;
left = i + 1;
}
}
window.insert(*cha, i);
});
result as i32
}
}
-----------------------------------------------------------
use std::collections::HashSet;
impl Solution {
pub fn length_of_longest_substring(s: String) -> i32 {
let mut left = 0;
let mut right = 0;
let mut result = 0;
let mut window = HashSet::new();
let s_arr:Vec<char> = s.chars().collect();
s_arr.iter().enumerate().for_each(|(i,cha)|{
while window.contains(cha) {
window.remove(&s_arr[left as usize]);
left += 1;
}
window.insert(cha);
right+=1;
result = result.max(right-left)
});
result
}
}
