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

字典中移除间隔n天内的日期,仅保留最后列出的日期

解决方案:按指定天数聚类日期并保留每组最后出现的日期

核心逻辑

将每个键对应的日期列表中,所有可通过≤n天间隔连通的日期归为一类(比如A和B间隔≤n、B和C间隔≤n,则A/B/C同组),仅保留该类在原列表中最后出现的日期;间隔超过n天的日期单独保留,最终输出顺序与原列表中保留元素的出现顺序一致。

代码实现

from datetime import date

def process_dates(date_list, n_days):
    # 转换日期并保留原列表索引
    date_with_metadata = []
    for idx, d_str in enumerate(date_list):
        year, month, day = map(int, d_str.split('-'))
        d = date(year, month, day)
        date_with_metadata.append((d, idx, d_str))
    
    # 并查集初始化
    parent = list(range(len(date_with_metadata)))
    
    def find(u):
        # 路径压缩优化
        while parent[u] != u:
            parent[u] = parent[parent[u]]
            u = parent[u]
        return u
    
    def union(u, v):
        # 合并两个集合
        u_root = find(u)
        v_root = find(v)
        if u_root != v_root:
            parent[v_root] = u_root
    
    # 按日期排序后,相邻合并连通的日期组
    sorted_dates = sorted(date_with_metadata, key=lambda x: x[0])
    for i in range(1, len(sorted_dates)):
        prev_date = sorted_dates[i-1][0]
        curr_date = sorted_dates[i][0]
        if (curr_date - prev_date).days <= n_days:
            # 合并原列表中对应的索引位置
            union(sorted_dates[i-1][1], sorted_dates[i][1])
    
    # 按聚类分组,保留每组中最后出现的日期(原索引最大)
    clusters = {}
    for idx in range(len(date_with_metadata)):
        root = find(idx)
        clusters.setdefault(root, []).append(date_with_metadata[idx])
    
    kept_dates = []
    for cluster in clusters.values():
        # 筛选原索引最大的元素
        last_appeared = max(cluster, key=lambda x: x[1])
        kept_dates.append((last_appeared[1], last_appeared[2]))
    
    # 按原列表顺序排序保留的日期
    kept_dates.sort(key=lambda x: x[0])
    return [d_str for _, d_str in kept_dates]

def process_date_dict(input_dict, n_days=30):
    output_dict = {}
    for key, dates in input_dict.items():
        output_dict[key] = process_dates(dates, n_days)
    return output_dict

测试示例

# 输入字典
input_dict = {
    'a': ['2020-12-11'],
    'b': ['2020-05-30', '2022-09-11'],
    'c': ['2021-07-28', '2022-07-20', '2022-07-07', '2022-06-30'],
    'd': ['2022-04-17', '2022-04-18', '2022-04-15', '2022-08-20']
}

# 处理(默认30天间隔)
result = process_date_dict(input_dict)
print(result)

输出结果:

{
    'a': ['2020-12-11'],
    'b': ['2020-05-30', '2022-09-11'],
    'c': ['2021-07-28', '2022-06-30'],
    'd': ['2022-04-15', '2022-08-20']
}

自定义天数用法

只需在调用时传入n_days参数即可,比如设置60天间隔:

result_60d = process_date_dict(input_dict, n_days=60)

效率说明

  • 并查集的操作时间复杂度近似为O(α(N))(α为阿克曼函数的反函数,几乎是常数)
  • 日期排序的时间复杂度为O(N log N)
  • 整体处理大列表时性能高效,适合批量处理日期数据

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.14 21:25:24