【Day 1】拒绝温水煮青蛙,从今天开始公开打卡 | LeetCode 3. 无重复字符的最长子串 + Go map 基础用法
-
今日打卡宣言 今天正式 Day 1!工作两年后明显感觉到技术停滞,项目忙+舒适区让我越来越没斗志。从今天起,用公开打卡逼自己每天进步一点,目标:连续100天不间断,年底前跳槽成功。欢迎大家监督我!
-
LeetCode 部分(核心)
已解答
中等
相关标签
相关企业
提示
给定一个字符串 s ,请你找出其中不含有重复字符的 最长 子串 ****的长度。
示例 1:
输入: s = "abcabcbb"
输出: 3
解释: 因为无重复字符的最长子串是 "abc",所以其长度为 3。注意 "bca" 和 "cab" 也是正确答案。
示例 2:
输入: s = "bbbbb"
输出: 1
解释: 因为无重复字符的最长子串是 "b",所以其长度为 1。
示例 3:
输入: s = "pwwkew"
输出: 3
解释: 因为无重复字符的最长子串是 "wke",所以其长度为 3。
请注意,你的答案必须是 子串 的长度,"pwke" 是一个子序列, 不是子串。
提示:
0 <= s.length <= 5 * 104s由英文字母、数字、符号和空格组成- 难度:中等
- 时间复杂度目标:O(n)
- 核心思路(3行以内): 用滑动窗口 + map 记录字符最后出现的位置,右指针遍历,遇到重复就移动左指针到上一次出现位置的下一位。窗口大小不断更新最大值。
- 代码(用 Go 写,面试常见):
Go
func lengthOfLongestSubstring(s string) int {
if len(s) == 0 {
return 0
}
charIndex := make(map[byte]int) // 字符 -> 最后出现的位置
maxLen, left := 0, 0
for right := 0; right < len(s); right++ {
if idx, ok := charIndex[s[right]]; ok && idx >= left {
left = idx + 1 // 移动左边界
}
charIndex[s[right]] = right
if right-left+1 > maxLen {
maxLen = right - left + 1
}
}
return maxLen
}
C++
class Solution {
public:
int lengthOfLongestSubstring(string s) {
// 核心思路, 滑动窗口加上map记录上一次相同字符的位置, 遇到相同的则left = idx + 1;
if (s.empty())
{
return 0;
}
int maxLen = 0, left = 0;
unordered_map<char, int> charIndex;
for (int right = 0; right < s.size(); right ++)
{
if (charIndex.count(s[right]))
{
left = max(left, charIndex[s[right]] + 1);
}
charIndex[s[right]] = right;
maxLen = max(maxLen, right - left + 1);
}
return maxLen;
}
};
-
易错点/优化点:
- 别用 charIndex[c] > left 判断,要 >= left(因为 left 刚好移动到重复位+1)
- map 用 byte 做 key 比 rune 更快(字符串是 byte 切片)
- 面试追问:如果要返回子串本身怎么改?(记录 maxStart + maxLen)
-
知识点部分(今天选 Go 基础,简单上手) Go map 的基础用法 & 常见面试点
-
声明:m := make(map[keyType]valueType) 或 var m map[keyType]valueType(后者是 nil map,不能直接赋值)
-
增删查:m[key] = val、delete(m, key)、val, ok := m[key]
-
面试常问:
- map 是线程安全的吗?(不是!并发读写 panic,用 sync.Map 或加锁)
- 为什么 key 不能是 slice/func/map?(因为需要 hash,且 slice 等不可比较)
- 今天题目中 map[byte]int 的优势:byte 是 uint8,hash 快,内存小。
-
-
今日感悟 其实这道题我以前刷过,但今天手写才发现自己对“左指针为什么移动到 idx+1”理解得不够透彻。公开打卡的好处就是:不敢水,必须搞懂再发。感觉第一步已经迈出去了,虽然小,但很踏实。
-
明天见!