返回

严谨!LeetCode 打卡:捕获捉迷藏数字

前端

序章:迷藏数字现身记

在算法的王国里,有一个有趣的问题,叫做「丢失的数字」。题目是这样说的:给定一个包含 [0, n] 中 n 个数的数组 nums,找出 [0, n] 这个范围内没有出现在数组 nums 中的那个数字。

第一幕:缜密策划,算法思路

  1. 确定范围:

    • 题目告诉我们数组 nums 中的数字范围是 [0, n],这意味着丢失的数字必定在 [0, n] 中。
    • 因此,我们的算法首先要创建一个从 0 到 n 的数组,称为 expected_nums。
  2. 标记出现:

    • 然后,我们需要遍历数组 nums,并将出现的数字在 expected_nums 中标记为已出现。
    • 标记的方法可以是将 expected_nums 中对应位置的值设置为 True。
  3. 寻找丢失:

    • 标记完成后,遍历 expected_nums,寻找其中为 False 的位置。
    • 这个位置对应的数字就是我们丢失的数字。

第二幕:编码艺术,Python 实现

def find_missing_number(nums):
  """
  查找 [0, n] 范围内,未出现在数组 nums 中的那个数字。

  参数:
    nums: 包含 [0, n] 中 n 个数的数组。

  返回:
    丢失的数字。
  """

  # 创建一个从 0 到 n 的数组,表示所有应该出现的数字。
  expected_nums = [True] * (len(nums) + 1)

  # 标记数组 nums 中出现的数字。
  for num in nums:
    expected_nums[num] = False

  # 寻找丢失的数字。
  for i, is_present in enumerate(expected_nums):
    if is_present:
      return i

  # 如果没有丢失的数字,则返回 -1。
  return -1


# 测试代码
nums = [3, 0, 1]
missing_number = find_missing_number(nums)
print(missing_number)  # 输出:2

第三幕:扩展思考,挑战升级

  1. 时间复杂度与空间复杂度:

    • 上述算法的时间复杂度为 O(n),其中 n 是数组 nums 的长度。
    • 空间复杂度为 O(n),因为我们需要创建一个大小为 n + 1 的数组 expected_nums。
  2. 优化算法:

    • 如果我们知道数组 nums 中的数字是随机分布的,那么我们可以使用位运算来优化算法。
    • 位运算的复杂度为 O(n),空间复杂度为 O(1)。
  3. 更多思考:

    • 如果数组 nums 中有重复数字,算法是否仍然有效?
    • 如果数组 nums 中有负数,算法是否仍然有效?
    • 如果数组 nums 的范围是 [a, b],其中 a 和 b 是任意整数,算法是否仍然有效?

尾声:拨开迷雾,算法之美

「丢失的数字」问题是一个经典的算法题,它考察了我们对数组、循环和集合等数据结构的理解。通过解决这个问题,我们可以进一步加深对算法的认识,并提升我们的编程能力。

在算法的王国里,还有许许多多有趣的问题等待着我们去探索。只要我们保持好奇心和学习热情,就一定能够在算法的世界里不断进步,不断成长。