给定一个未排序的整数数组 nums ,找出数字连续的最长序列(不要求序列元素在原数组中连续)的长度。
请你设计并实现时间复杂度为 O(n) 的算法解决此问题。
示例 1:
输入:nums = [100,4,200,1,3,2]
输出:4
解释:最长数字连续序列是 [1, 2, 3, 4]。它的长度为 4。
示例 2:
输入:nums = [0,3,7,2,5,8,4,6,0,1]
输出:9
提示:
0 <= nums.length <= 10^5
-10^9 <= nums[i] <= 10^9
解法:哈希表 字典
用哈希表存储每个端点值对应连续区间的长度
若数已在哈希表中:跳过不做处理
若是新数加入:
- 取出其左右相邻数已有的连续区间长度 left 和 right
- 计算当前数的区间长度为:length = left + right + 1
- 根据length更新最大长度res的值
- 更新区间两端点的长度值
代码实现:
class Solution:
def longestConsecutive(self, nums: List[int]) -> int:
res = 0
hash_dict = dict()
for num in nums:
if num not in hash_dict: # 新进来哈希表一个数
left = hash_dict.get(num-1,0) # 获取当前数的最左边连续长度,没有的话就更新为0
right = hash_dict.get(num+1,0) # 同理获取右边的数
"""不用担心左边和右边没有的情况
因为没有的话就是left或者right0
并不改变什么
"""
#print('num:',num)
#print('left:',left)
#print('right:',right)
hash_dict[num] = 1 # 把当前数加入哈希表,代表当前数字出现过
length = left+1+right # 更新长度
res = max(res,length)
hash_dict[num-left] = length # 更新最左端点的值,如果left=n存在,那么证明当前数的前n个都存在哈希表中
hash_dict[num+right] = length # 更新最右端点的值,如果right=n存在,那么证明当前数的后n个都存在哈希表中
# 此时 【num-left,num-right】范围的值都连续存在哈希表中了
# 即使left或者right=0都不影响结果
#print('hash_dict:',hash_dict)
return res
为方便只看代码,把注释删掉的版本:
class Solution:
def longestConsecutive(self, nums: List[int]) -> int:
res = 0
hash_dict = dict()
for num in nums:
if num not in hash_dict:
left = hash_dict.get(num-1,0)
right = hash_dict.get(num+1,0)
hash_dict[num] = 1
length = left+1+right
res = max(res,length)
hash_dict[num-left] = length
hash_dict[num+right] = length
return res
print的输出过程:
以示例1为例:
num: 100
left: 0
right: 0
hash_dict: {100: 1}
num: 4
left: 0
right: 0
hash_dict: {100: 1, 4: 1}
num: 200
left: 0
right: 0
hash_dict: {100: 1, 4: 1, 200: 1}
num: 1
left: 0
right: 0
hash_dict: {100: 1, 4: 1, 200: 1, 1: 1}
num: 3
left: 0
right: 1
hash_dict: {100: 1, 4: 2, 200: 1, 1: 1, 3: 2}
num: 2
left: 1
right: 2
hash_dict: {100: 1, 4: 4, 200: 1, 1: 4, 3: 2, 2: 1}
以示例2为例:
num: 0
left: 0
right: 0
hash_dict: {0: 1}
num: 3
left: 0
right: 0
hash_dict: {0: 1, 3: 1}
num: 7
left: 0
right: 0
hash_dict1: {0: 1, 3: 1}
hash_dict2: {0: 1, 3: 1, 7: 1}
num: 2
left: 0
right: 1
hash_dict: {0: 1, 3: 2, 7: 1, 2: 2}
num: 5
left: 0
right: 0
hash_dict: {0: 1, 3: 2, 7: 1, 2: 2, 5: 1}
num: 8
left: 1
right: 0
hash_dict: {0: 1, 3: 2, 7: 2, 2: 2, 5: 1, 8: 2}
num: 4
left: 2
right: 1
hash_dict: {0: 1, 3: 2, 7: 2, 2: 4, 5: 4, 8: 2, 4: 1}
num: 6
left: 4
right: 2
hash_dict: {0: 1, 3: 2, 7: 2, 2: 7, 5: 4, 8: 7, 4: 1, 6: 1}
num: 1
left: 1
right: 7
hash_dict: {0: 9, 3: 2, 7: 2, 2: 7, 5: 4, 8: 9, 4: 1, 6: 1, 1: 1}