You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Python 3.11中如何批量删除字典内过期的datetime键值对?

筛选字典中键不早于当前时间的元素(支持无序字典)

问题背景

使用Python 3.11,现有一个以datetime对象为键、字符串为值的字典:

import datetime

dates = {
    datetime.datetime(2022, 1, 1): "a", 
    datetime.datetime(2022, 5, 4): "b",
    datetime.datetime(2022, 9, 25): "c",
    datetime.datetime(2023, 5, 17): "d",
    datetime.datetime(2023, 12, 15): "e",
    datetime.datetime(2024, 3, 17): "f",
    datetime.datetime(2024, 4, 3): "g"
} 

需要删除所有键早于当前时间的元素,例如当当前时间为datetime.datetime(2024, 2, 9)时,结果应为:

{
    datetime.datetime(2024, 3, 17): "f",
    datetime.datetime(2024, 4, 3): "g"
} 

此前的代码仅在字典按键排序时生效,但实际字典可能无序:

new_dates = {}
now = datetime.datetime.now()
for k, v in reversed(dates.items()):
    if k < now:
        break
    new_dates[k] = v

解决方案

方案1:标准库实现(无第三方依赖)

虽然无法完全避免遍历,但可以通过排序+二分查找减少后续处理的元素数量,完美适配无序字典:

  1. 提取所有键并排序
  2. 用bisect模块快速定位第一个不早于当前时间的键的位置
  3. 从该位置提取键值对构建新字典

代码示例:

import datetime
import bisect

dates = {
    datetime.datetime(2022, 1, 1): "a", 
    datetime.datetime(2022, 5, 4): "b",
    datetime.datetime(2022, 9, 25): "c",
    datetime.datetime(2023, 5, 17): "d",
    datetime.datetime(2023, 12, 15): "e",
    datetime.datetime(2024, 3, 17): "f",
    datetime.datetime(2024, 4, 3): "g"
} 

now = datetime.datetime(2024, 2, 9)
sorted_keys = sorted(dates.keys())
# 找到第一个 >= now 的键的索引
idx = bisect.bisect_left(sorted_keys, now)
# 仅保留符合条件的键值对
new_dates = {k: dates[k] for k in sorted_keys[idx:]}

print(new_dates)

该方法时间复杂度为O(n log n)(排序的开销),后续仅遍历需要保留的元素,比全遍历更高效(当需保留元素占比小时)。

方案2:第三方有序字典(适合频繁查询场景)

如果需要频繁进行这类时间范围筛选,推荐使用sortedcontainers库的SortedDict——它内部维护有序的键,支持快速范围查询:

  1. 先安装库:pip install sortedcontainers
  2. 用SortedDict存储数据
  3. 调用irange方法直接获取符合条件的键值对

代码示例:

import datetime
from sortedcontainers import SortedDict

dates = SortedDict({
    datetime.datetime(2022, 1, 1): "a", 
    datetime.datetime(2022, 5, 4): "b",
    datetime.datetime(2022, 9, 25): "c",
    datetime.datetime(2023, 5, 17): "d",
    datetime.datetime(2023, 12, 15): "e",
    datetime.datetime(2024, 3, 17): "f",
    datetime.datetime(2024, 4, 3): "g"
}) 

now = datetime.datetime(2024, 2, 9)
# 直接提取所有键 >= now 的键值对,转成普通字典
new_dates = dict(dates.irange(minimum=now))

print(new_dates)

该方法单次查询时间复杂度为O(log n + k)(k为结果元素数量),无需每次排序,适合高频筛选场景。


内容的提问来源于stack exchange,提问作者Tamames

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.30 10:03:34