📅 刷题 Day 38
关键词:数组、哈希表、去重、O(n)、连续性判断
第一章:数列小镇的连号骚动
在一个叫 nums
的小镇上,居民们一直以来过着井然有序的生活------只要大家都能顺着住,比如 [1, 2, 3, 4]
连号排排坐,大家就其乐融融。
直到有一天,小镇来了几个重复户口的人,比如两个 "1" 和两个 "2",这下镇长大雄慌了:"哆啦A梦,我怎么知道他们到底谁在串门?最长连续住户到底有几个?"
第二章:去重风暴之谜
大雄赶紧抄起老本行------排序!
ini
function longestConsecutive(nums: number[]): number {
if (nums.length === 0) return 0;
let numArr = Array.from(nums.sort((a, b) => a - b));
let max = 1, count = 1, last = numArr[0];
for (let i = 1; i < numArr.length; i++) {
if (last + 1 === numArr[i]) {
count++;
max = Math.max(max, count);
} else {
count = 1;
}
last = numArr[i];
}
return max;
}
但很快,问题来了。
测试输入:
ini
nums = [1, 0, 1, 2];
输出:
2 ❌
"怎么才算出 2?明明有 0, 1, 2 啊!"
第三章:哆啦A梦出手 · 去重救场!
哆啦A梦一口铜锣烧没咽住:"你是不是忘了 ------ 有人重复登记户口了。"
原数组 [1, 0, 1, 2]
排序后是 [0, 1, 1, 2]
于是遍历时会跳过第二个 1,把连续性判成了"0,1" 和 "1,2" 两段不相连的序列!
💥 重复项直接破坏了连续判断逻辑!
于是大雄马上更新版本:
javascript
let numArr = Array.from(new Set(nums.sort((a, b) => a - b)));
Set 一出手,重复一个不留!连续逻辑完美恢复 ✅
第四章:O(nlogn)警告来袭
"可是,这样排序之后虽然对了,复杂度也变成 O(nlogn) 了哎~"
大雄不安地搓搓手。
哆啦A梦摸出一本《算法复杂度法规》:
"题目明明写着要你用 O(n)!你这违章操作可不行!"
第五章:哈希流派的连号核爆
"别怕,我还有最后的秘密武器!"
哆啦A梦从四维口袋掏出一把"哈希能量枪":
ini
function longestConsecutive(nums: number[]): number {
const numSet = new Set(nums);
let maxLen = 0;
for (const num of numSet) {
// 只有 num 是序列起点,才开始扩展
if (!numSet.has(num - 1)) {
let current = num;
let count = 1;
while (numSet.has(current + 1)) {
current++;
count++;
}
maxLen = Math.max(maxLen, count);
}
}
return maxLen;
}
💡 起点判断 + 向后扫描 + 去重保障唯一性
------每个数字只访问一次,完美 O(n)!
第六章:为什么必须去重?
🎯 原因一 :重复元素在"连续性"中毫无意义,只会干扰判断
🎯 原因二 :重复元素可能导致判断 last + 1 === current
失败,从而断开原本是连续的序列
🎯 原因三:多次出现的数字若不去重,可能让连续计数"中断重启",错失最长结果
举个栗子:
ini
nums = [1, 0, 1, 2]
不去重排序后 → [0, 1, 1, 2]
last = 0
current = 1 ✅
last = 1
current = 1 ❌ (跳过!导致 1→2 连接断了)
第七章:技术启示录
解法 | 是否正确 | 时间复杂度 | 是否符合要求 |
---|---|---|---|
排序 + 遍历 | ✅ | O(nlogn) | ❌ |
排序 + 去重 | ✅ | O(nlogn) | ❌ |
Set + 起点扫描 | ✅ | O(n) | ✅ |
第八章:铜锣烧总结局
"所以我们不仅要排序,还得去重 ,然后还要换种逻辑思路 ,才能解出真正的'连续'。"
大雄一边总结,一边给哆啦A梦递上一盒热腾腾的铜锣烧。
哆啦A梦边吃边点头:"做题就像做铜锣烧,顺序对、配料准,才能香甜出炉。"
窗外传来胖虎的咆哮:
"谁把我家的 3 连号房抢成了 [1,2,3,4]?!我明明登记了两个 3 啊!"
哆啦A梦冷笑:
"重复登记,不算连续!"