代码之家  ›  专栏  ›  技术社区  ›  Paul Stephenson

Python中向datetime.time添加N秒的标准方法是什么?

  •  517
  • Paul Stephenson  · 技术社区  · 17 年前

    给定a datetime.time Python中的value,是否有标准的方法向其添加整数秒数,以便 11:34:59 3. 11:35:02 例如?

    这些显而易见的想法行不通:

    >>> datetime.time(11, 34, 59) + 3
    TypeError: unsupported operand type(s) for +: 'datetime.time' and 'int'
    >>> datetime.time(11, 34, 59) + datetime.timedelta(0, 3)
    TypeError: unsupported operand type(s) for +: 'datetime.time' and 'datetime.timedelta'
    >>> datetime.time(11, 34, 59) + datetime.time(0, 0, 3)
    TypeError: unsupported operand type(s) for +: 'datetime.time' and 'datetime.time'
    

    最后我写了这样的函数:

    def add_secs_to_time(timeval, secs_to_add):
        secs = timeval.hour * 3600 + timeval.minute * 60 + timeval.second
        secs += secs_to_add
        return datetime.time(secs // 3600, (secs % 3600) // 60, secs % 60)
    

    不过,我忍不住想,我错过了一种更容易做到这一点的方法。

    相关的

    11 回复  |  直到 8 年前
        1
  •  412
  •   paxdiablo    12 年前

    您可以使用完整 datetime 变量与 timedelta ,并提供一个虚拟日期,然后使用 time 只是为了得到时间值。

    例如:

    import datetime
    a = datetime.datetime(100,1,1,11,34,59)
    b = a + datetime.timedelta(0,3) # days, seconds, then other fields.
    print(a.time())
    print(b.time())
    

    结果为两个值,相隔三秒:

    11:34:59
    11:35:02
    

    你也可以选择更易读的

    b = a + datetime.timedelta(seconds=3)
    

    如果你愿意的话。


    如果你想要一个可以做到这一点的函数,你可以考虑使用 addSecs 在......下面

    import datetime
    
    def addSecs(tm, secs):
        fulldate = datetime.datetime(100, 1, 1, tm.hour, tm.minute, tm.second)
        fulldate = fulldate + datetime.timedelta(seconds=secs)
        return fulldate.time()
    
    a = datetime.datetime.now().time()
    b = addSecs(a, 300)
    print(a)
    print(b)
    

    这将输出:

     09:11:55.775695
     09:16:55
    
        2
  •  44
  •   Eli Courtwright    17 年前

    正如这里的其他人所说,你可以在整个过程中使用完整的datetime对象:

    from datetime import datetime, date, time, timedelta
    sometime = time(8,00) # 8am
    later = (datetime.combine(date.today(), sometime) + timedelta(seconds=3)).time()
    

    然而,我认为有必要解释为什么需要完整的日期时间对象。考虑一下,如果我在晚上11点加上2个小时,会发生什么。正确的行为是什么?例外,因为你的时间不能超过晚上11:59?它应该绕回去吗?

    不同的程序员会有不同的期望,所以无论他们选择什么结果,都会让很多人感到惊讶。更糟糕的是,程序员在最初测试时会编写运行良好的代码,然后通过做一些意想不到的事情让它崩溃。这非常糟糕,这就是为什么不允许将timedelta对象添加到时间对象中。

        3
  •  18
  •   unmounted    17 年前

    有一件小事,可能会增加几秒钟内覆盖默认值的清晰度

    >>> b = a + datetime.timedelta(seconds=3000)
    >>> b
    datetime.datetime(1, 1, 1, 12, 24, 59)
    
        4
  •  9
  •   Paul Stephenson    17 年前

    您不能简单地将数字添加到 datetime 因为不清楚使用了什么单位:秒、小时、周。..

    这是 timedelta 用于操作日期和时间的类。 日期时间 日期时间 提供 时间增量 , 日期时间 时间增量 提供 日期时间 ,两个 日期时间 虽然有两个对象,但无法添加 时间增量 可以。

    创建 时间增量 对象,显示要添加的秒数,并将其添加到 日期时间 对象:

    >>> from datetime import datetime, timedelta
    >>> t = datetime.now() + timedelta(seconds=3000)
    >>> print(t)
    datetime.datetime(2018, 1, 17, 21, 47, 13, 90244)
    

    C++中也有同样的概念: std::chrono::duration .

        5
  •  6
  •   rescdsk    13 年前

    感谢@Pax Diablo、@bvmou和@Arachnid建议在整个过程中使用完整的日期时间。如果我必须接受来自外部源的datetime.time对象,那么这似乎是一种替代方案 add_secs_to_time() 功能:

    def add_secs_to_time(timeval, secs_to_add):
        dummy_date = datetime.date(1, 1, 1)
        full_datetime = datetime.datetime.combine(dummy_date, timeval)
        added_datetime = full_datetime + datetime.timedelta(seconds=secs_to_add)
        return added_datetime.time()
    

    这段冗长的代码可以压缩成一行:

    (datetime.datetime.combine(datetime.date(1, 1, 1), timeval) + datetime.timedelta(seconds=secs_to_add)).time()
    

    但无论如何,为了代码的清晰性,我想把它封装在一个函数中。

        6
  •  4
  •   George Sovetov    7 年前

    如果值得在项目中添加另一个文件/依赖项,我刚刚编写了一个扩展 datetime.time 有算术能力。当你过了午夜,它大约在零度左右。现在,“24小时后会是什么时候”有很多极端情况,包括夏令时、闰秒、历史时区变化等。但有时你真的需要简单的情况,这就是它的作用。

    你的例子可以写成:

    >>> import datetime
    >>> import nptime
    >>> nptime.nptime(11, 34, 59) + datetime.timedelta(0, 3)
    nptime(11, 35, 2)
    

    nptime 继承自 datetime.time ,因此这些方法中的任何一种都应该是可用的。

    它可以从PyPi获得 nptime (“非迂腐的时间”),或在GitHub上: https://github.com/tgs/nptime

        7
  •  1
  •   Tshilidzi Mudau Simon Müller    8 年前

    在现实世界的环境中,单独与某人合作从来都不是一个好主意 time ,始终使用 datetime ,甚至更好 utc ,以避免夜间、夏令时、用户和服务器之间的不同时区等冲突。

    所以我推荐这种方法:

    import datetime as dt
    
    _now = dt.datetime.now()  # or dt.datetime.now(dt.timezone.utc)
    _in_5_sec = _now + dt.timedelta(seconds=5)
    
    # get '14:39:57':
    _in_5_sec.strftime('%H:%M:%S')
    
        8
  •  1
  •   Bart Van Loon    6 年前

    为了完整起见,这里有一个方法 arrow (Python的更好日期和时间):

    sometime = arrow.now()
    abitlater = sometime.shift(seconds=3)