力扣刷题笔记-03
03 无重复字符的最长子串
我的思路
明确问题
- 怎么判断字符串是不是重复
答:hashset的contains,把字符放进集合里。
chatGPT
滑动窗口
- 定义两个指针,分别是left和right,用来指向不重复的子字符串。初始时候两个字符串都指向字符串的开头
- 用HashSet存储当前窗口里的元素,用int max变量存储最大的子串长度
- 开始遍历,right指针移动,先判断是不是包含在集合里,不包含的话放进去,用Math.max判断最大子串;包含的话,left指针所在的那个字符从集合里面移除来,left右移。
- 重复3
- while循环的出口在right指针指向最后一个字符的时候
这个算法目前的时间复杂度挺高,应该用hashmap存储字符和索引
class Solution {
public int lengthOfLongestSubstring(String s) {
if (s == null || s.length() == 0) {
return 0;
}
// 达摩克利斯之剑始终高悬,裁员的屠刀时刻垂直
// 用HashSet来保存滑动窗口里面的数据
HashSet<Character> set = new HashSet<>();
// 用来记录无重复的子串的长度
int maxLength = 0;
// 初始时刻,窗口两端的指针都指向0
int left = 0;
int right = 0;
while (right < s.length()) {
char currentChar = s.charAt(right);
if (!set.contains(currentChar)) {
// 字符放进滑动窗口里
set.add(currentChar);
/**
* 这行代码是我认为整个算法最巧妙的地方
* 为什么要取max呢?
* 滑动窗口只保证里面的字符串是不重复的,不管是不是最长的
* 所以我们每次窗口滑动的时候,就要计算一下最大长度,保存下来。
*/
maxLength = Math.max(maxLength, right - left + 1);
// right指针右移
right++;
} else {
// 进到这里说明有重复的元素,left指针右移
set.remove(s.charAt(left));
left++;
}
}
return maxLength;
}
}