找单独数 | 豆包MarsCode AI刷题

58 阅读3分钟

题目解析: 这是一个经典的"寻找单一元素"问题,虽然题目包装成了班级和卡片的场景,但本质是在一个数组中找出唯一一个出现一次的数字。这类问题在实际编程中也经常遇到,比如在数据处理、文件校验等场景中。

关键特征分析:

  1. 数组长度为奇数(这很重要,因为除了一个数出现一次,其他都出现两次)
  2. 除了一个数字外,其他数字都恰好出现两次(不多不少)
  3. 要求时间复杂度O(n)
  4. 要求尽量减少额外空间使用

解题思路分析:

  1. 暴力解法(不推荐):

    • 对于每个数字,遍历整个数组统计其出现次数
    • 时间复杂度O(n²),不符合要求
    • 这种方法简单直观,但效率低下
  2. 哈希表解法:

    • 使用哈希表记录每个数字出现的次数
    • 时间复杂度O(n),空间复杂度O(n)
    • 虽然满足时间要求,但空间复杂度较高
    • 实现简单,适合面试时快速编码
  3. 排序解法:

    • 先将数组排序,然后比较相邻元素
    • 时间复杂度O(nlogn),不符合要求
    • 但这种方法可以不需要额外空间
  4. 最优解法(异或运算):

    • 利用异或运算的特性来解决
    • 时间复杂度O(n),空间复杂度O(1)
    • 完美满足所有要求

异或解法详细分析:

  1. 异或运算的特性:

    • a ⊕ a = 0(任何数与自己异或等于0)
    • a ⊕ 0 = a(任何数与0异或等于它本身)
    • 异或运算满足交换律和结合律
  2. 解题步骤:

    • 初始化结果变量 result = 0
    • 遍历数组中的每个元素,与result进行异或运算
    • 最终result就是只出现一次的数字
  3. 原理解释:

    • 当数组中的所有数字都参与异或运算时
    • 出现两次的数字会相互抵消(因为a⊕a=0)
    • 最后只剩下那个出现一次的数字(因为0⊕a=a)

代码实现思路:

python
CopyInsert
def findSingleNumber(cards):
    result = 0
    for num in cards:
        result ^= num
    return result

这个解法的优点:

  1. 时间复杂度为O(n),只需要遍历一次数组
  2. 空间复杂度为O(1),只使用一个变量
  3. 代码简洁优雅,易于理解和维护
  4. 不需要额外的排序或数据结构

实际应用扩展:

  1. 这种解法不仅适用于找出现一次的数字,还可以扩展到其他类似问题
  2. 在实际工程中,可以用于数据校验、文件完整性检查等场景
  3. 异或运算在底层实现非常快,因此这种解法在实际运行时非常高效

需要注意的边界情况:

  1. 数组长度为1时的处理
  2. 数组中包含0时的处理
  3. 数组中的数字较大时的处理

总的来说,这是一道考察位运算和算法优化能力的好题目。通过这道题,我们可以学习到:

  1. 如何从暴力解法逐步优化到最优解
  2. 位运算在算法优化中的重要作用