3分钟解决数组去重难题:GitHub热门LeetCode解题库实战指南

3分钟解决数组去重难题:GitHub热门LeetCode解题库实战指南

【免费下载链接】LeetCode-Book 《剑指 Offer》 Python, Java, C++ 解题代码,LeetBook《图解算法数据结构》配套代码仓 【免费下载链接】LeetCode-Book 项目地址: https://gitcode.com/GitHub_Trending/le/LeetCode-Book

你是否还在为数组去重问题浪费30分钟以上?是否遇到过空间复杂度超标的情况?本文将通过GitHub热门项目GitHub_Trending/le/LeetCode-Book中的经典题型,教你用两种高效策略解决数组重复元素查找问题,看完即可掌握时间复杂度O(N)、空间复杂度O(1)的最优解法。

问题定义与应用场景

在开发中,数组去重是数据处理的基础操作,例如:

  • 用户ID列表去重
  • 日志数据清洗
  • 表单提交重复检测

本问题来源于剑指 Offer 03. 数组中重复的数字,要求在长度为n的数组nums中找出重复数字,数组元素取值范围为0~n-1。

方法一:哈希表追踪法

算法原理

利用哈希表(Hash Set)的O(1)查找特性,遍历数组过程中记录已出现元素,遇到重复立即返回。

实现步骤

  1. 初始化空集合dic
  2. 遍历数组每个元素:
    • 若元素已在集合中,返回该元素
    • 否则将元素加入集合
  3. 遍历结束未找到时返回-1(本题保证有重复元素)

代码实现

class Solution:
    def findRepeatNumber(self, nums: [int]) -> int:
        dic = set()
        for num in nums:
            if num in dic: return num
            dic.add(num)
        return -1

完整代码示例可查看:sword_for_offer/docs/剑指 Offer 03. 数组中重复的数字.md

复杂度分析

  • 时间复杂度:O(N) - 只需遍历一次数组
  • 空间复杂度:O(N) - 最坏情况需存储所有不重复元素

方法二:原地索引交换法

算法突破点

题目特殊条件:所有数字都在0 ~ n-1范围内,意味着数组元素与索引存在一一对应关系,可通过索引重排实现原地去重。

核心思路

通过交换操作将每个元素放到其对应索引位置,当发现目标索引已存在相同元素时,即为重复值。

操作流程

  1. 遍历数组,设当前索引为i:
    • nums[i] == i:元素已在正确位置,继续下一个
    • nums[nums[i]] == nums[i]:发现重复,返回该元素
    • 否则:交换nums[i]nums[nums[i]]

动图演示

<原地交换法演示>

代码实现

class Solution:
    def findRepeatNumber(self, nums: List[int]) -> int:
        i = 0
        while i < len(nums):
            if nums[i] == i:
                i += 1
                continue
            if nums[nums[i]] == nums[i]: return nums[i]
            nums[nums[i]], nums[i] = nums[i], nums[nums[i]]
        return -1

复杂度分析

  • 时间复杂度:O(N) - 每个元素最多交换两次
  • 空间复杂度:O(1) - 无需额外空间

两种方法对比与选择建议

方法时间复杂度空间复杂度适用场景
哈希表法O(N)O(N)数据范围无限制时
原地交换法O(N)O(1)元素范围0~n-1的特殊数组

扩展练习与项目资源

相似题型推荐

项目完整代码

刷题计划

建议结合项目中的剑指 Offer 刷题计划.md进行系统训练,按题目分类.md逐步攻克数组、链表、树等数据结构类型题。

掌握这两种方法后,数组去重类问题就能迎刃而解。收藏本文,下次遇到类似问题直接套用,让你的代码既高效又优雅!

【免费下载链接】LeetCode-Book 《剑指 Offer》 Python, Java, C++ 解题代码,LeetBook《图解算法数据结构》配套代码仓 【免费下载链接】LeetCode-Book 项目地址: https://gitcode.com/GitHub_Trending/le/LeetCode-Book

创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值