1. 题目描述
小C拿到了一个空集,她准备进行以下操作:将区间 [l, r] 内的每个整数添加进集合。每次操作后,她需要输出当前集合的 mex。
定义: 集合的 mex(最小排除值)是指集合中最小的未出现的非负整数。
输入:
- 整数
q表示操作的次数。 - 一个包含
q个查询的列表queries,每个查询是一个列表[l, r],表示在集合中添加区间[l, r]中的所有整数。
输出:
- 一个列表,包含每次操作后集合的 mex。
2. 题目解析
mex 的含义:
mex是最小的非负整数,且不在当前集合中。例如,如果集合是{0, 1, 3, 4},那么mex就是2,因为0和1已经出现了,2是最小的未出现的数字。
思考过程:
- 集合维护: 我们用一个集合
current_set来维护当前集合的元素。 - mex 更新: 每次加入新元素时,我们需要重新计算 mex。最直观的做法是从当前 mex 开始检查,如果
mex不在集合中,则返回当前 mex,否则递增直到找到一个未出现的数字。 - 高效性: 在每次操作时,需要快速更新集合并计算 mex,尤其是当加入的区间范围较大时,我们需要确保方法的效率。
3. 思考过程
为了实现高效的 mex 计算,我们可以采取以下策略:
- 集合存储: 使用 Python 的
set数据结构,因为set支持高效的元素查找和插入。 - mex 计算: 初始时,mex 从
0开始,我们每次操作后检查mex是否在集合中。如果在集合中,我们递增mex并检查新的mex是否存在,直到找到一个不在集合中的数字。 - 批量加入区间: 对于每个查询
[l, r],我们需要将区间内的所有整数添加到集合中。由于区间可能较大,直接遍历区间并将每个数字加入集合。
4. 解题代码
初始化变量和集合
result = [] # 用于存储每次操作后的 mex
current_mex = 0 # 当前的 mex,初始值为 0
current_set = set() # 用于存储当前集合
result用来存储每次操作后的mex。current_mex用来追踪当前的 mex,初始化为0。current_set用来存储当前集合中的元素,使用set来确保查找和插入的高效性。
遍历每个查询,更新集合并计算 mex
for l, r in queries:
# 将区间 [l, r] 内的每个数字添加到 current_set 中
for num in range(l, r + 1):
current_set.add(num)
# 更新 mex,直到找到一个未出现在集合中的 mex
while current_mex in current_set:
current_mex += 1
# 记录当前的 mex
result.append(current_mex)
- 遍历每个查询
[l, r]。 - 对于每个查询中的区间
[l, r],将区间内的所有整数添加到current_set中。 - 然后,我们通过
while current_mex in current_set:循环检查并更新mex。如果当前的mex已在集合中,递增mex直到找到一个不在集合中的最小值。 - 每次更新
mex后,将其添加到result列表中。
返回结果
return result
- 返回最终存储所有 mex 的
result列表。
测试代码
if __name__ == '__main__':
# 测试用例
print(solution(4, [[1, 3], [7, 8], [0, 5], [3, 6]]) == [0, 0, 6, 9])
print(solution(3, [[0, 2], [3, 4], [6, 10]]) == [3, 5, 5])
print(solution(2, [[2, 5], [7, 9]]) == [0, 0])
- 测试了三个不同的测试用例,确保每次操作后 mex 的计算符合预期。
5. MarsCode 帮助了我什么?
MarsCode 在我解决这个问题的过程中提供了以下几方面的帮助:
- 优化数据结构选择: 我最初使用了
list来存储集合元素,而 MarsCode 推荐我使用set,因为set的查找和插入操作更高效,特别是在集合较大时。 - mex 计算的优化: 在最初的思路中,我是通过每次从
0开始检查整个集合中的元素来计算 mex,效率较低。MarsCode 提供了递增mex的思路,避免了不必要的检查,从而提高了效率。 - 代码重构和简化: MarsCode 使我意识到代码可以通过简化循环和移除冗余部分来优化,从而使代码更加简洁易懂。
6. 总结
通过这道题,我深刻理解了如何在动态更新集合的过程中计算 mex。在面对类似问题时,选择合适的数据结构和优化算法是至关重要的。此外,MarsCode 提供的帮助让我更加高效地解决了问题,优化了我的代码设计和实现。通过这一过程,我不仅提升了自己的编程能力,也学到了如何更好地优化解决方案,提高效率。
希望在未来,能够借助 MarsCode 继续解决更多复杂的编程问题,不断提升自己!