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

Python Numpy对比日期序列提取占用/未占用连续区间的起止值

实现代码

from datetime import datetime

# 样例输入
dates = ['2021-08-15 03:16:34', '2021-08-15 03:17:24', '2021-08-15 03:20:02', '2021-08-15 05:56:17', '2021-08-15 05:57:01', '2021-08-15 07:49:00', '2021-08-15 07:49:02', '2021-08-15 07:51:15', '2021-08-15 07:51:34', '2021-08-15 08:33:39']
selected_dates= ['2021-08-15 03:16:34', '2021-08-15 03:17:24', '2021-08-15 07:49:02', '2021-08-15 07:51:15', '2021-08-15 07:51:34']

# 1. 日期格式转换,先对原始日期去重排序避免输入乱序的问题
date_list = sorted([datetime.strptime(d, "%Y-%m-%d %H:%M:%S") for d in set(dates)])
selected_set = set([datetime.strptime(d, "%Y-%m-%d %H:%M:%S") for d in selected_dates])

# 2. 合并连续区间,这里的连续默认指在排序后的日期列表中状态连续
# 如果需要按时间间隔判断连续(比如间隔超过1分钟就算断开),可以自己调整判断阈值
occupying = []
non_occupying = []
if date_list:
    # 初始化第一个区间的状态、起止时间
    current_status = date_list[0] in selected_set
    current_start = current_end = date_list[0]
    
    for d in date_list[1:]:
        status = d in selected_set
        # 状态相同就延长当前区间,要加时间间隔判断的话在这里加条件即可
        # 比如改成 if status == current_status and (d - current_end).total_seconds() < 60: 就是间隔1分钟内算连续
        if status == current_status:
            current_end = d
        else:
            # 状态变化就把当前区间存入对应列表,重置区间参数
            if current_status:
                occupying.append((current_start, current_end))
            else:
                non_occupying.append((current_start, current_end))
            current_status = status
            current_start = current_end = d
    # 把最后一个未保存的区间存入列表
    if current_status:
        occupying.append((current_start, current_end))
    else:
        non_occupying.append((current_start, current_end))

# 3. 格式化输出
def format_interval(interval):
    start, end = interval
    start_str = start.strftime("%Y-%m-%d %H:%M:%S")
    end_str = end.strftime("%Y-%m-%d %H:%M:%S")
    return start_str if start == end else f"{start_str} - {end_str}"

print("Occupying dates: ")
for interval in occupying:
    print(format_interval(interval))
print("Non Occupying dates:")
for interval in non_occupying:
    print(format_interval(interval))

如果你要和给出的样例输出完全匹配,只需要把上面代码里的连续判断条件加上1分钟的时间间隔限制,也就是把if status == current_status:改成if status == current_status and (d - current_end).total_seconds() < 60:即可,输出和你给出的预期完全一致。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.10.05 13:06:03