5

假设我有 2 个时间间隔,例如 16:30 - 20:00 和 15:00 - 19:00,我需要找到这两个时间间隔之间的总时间,所以结果是 5 小时(我将两个时间间隔相加并减去相交区间),我如何编写一个通用函数来处理所有情况,例如一个区间在另一个区间(所以结果是更大的区间),没有交集(所以结果是两个区间的总和)。

我传入的数据结构是原始的,只是像“15:30”这样的字符串,因此可能需要进行转换。

谢谢

4

4 回答 4

4
from datetime import datetime, timedelta

START, END = xrange(2)
def tparse(timestring):
    return datetime.strptime(timestring, '%H:%M')

def sum_intervals(intervals):
    times = []
    for interval in intervals:
        times.append((tparse(interval[START]), START))
        times.append((tparse(interval[END]), END))
    times.sort()

    started = 0
    result = timedelta()
    for t, type in times:
        if type == START:
            if not started:
                start_time = t
            started += 1
        elif type == END:
            started -= 1
            if not started:
               result += (t - start_time) 
    return result

从问题中测试您的时间:

intervals = [
                ('16:30', '20:00'),
                ('15:00', '19:00'),
            ]
print sum_intervals(intervals)

打印:

5:00:00

与不重叠的数据一起测试

intervals = [
                ('16:30', '20:00'),
                ('15:00', '19:00'),
                ('03:00', '04:00'),
                ('06:00', '08:00'),
                ('07:30', '11:00'),
            ]
print sum_intervals(intervals)

结果:

11:00:00
于 2009-08-24T21:20:39.900 回答
0

我假设您可以自己转换为日期时间之类的东西。

将两个区间相加,然后减去任何重叠。您可以通过比较两个范围的最小值和最大值来获得重叠。

于 2009-08-24T21:12:39.603 回答
0

重叠时的代码,请将其添加到您的解决方案之一中:

def interval(i1, i2):
    minstart, minend = [min(*e) for e in zip(i1, i2)]
    maxstart, maxend = [max(*e) for e in zip(i1, i2)]

    if minend < maxstart: # no overlap
        return minend-minstart + maxend-maxstart
    else: # overlap
        return maxend-minstart
于 2009-08-24T21:30:44.670 回答
0

您需要将字符串转换为日期时间。您可以使用datetime.datetime.strptime.

给定datetime.datetime对象的间隔,如果间隔是:

int1 = (start1, end1)
int2 = (start2, end2)

那么不只是:

if end1 < start2 or end2 < start1:
    # The intervals are disjoint.
    return (end1-start1) + (end2-start2)
else:
    return max(end1, end2) - min(start1, start2)
于 2009-08-24T22:55:39.833 回答