为什么相同的日期时间不相等?

Why aren't identical datetimes equal?

提问人:Pete 提问时间:1/17/2023 最后编辑:Konrad RudolphPete 更新时间:1/17/2023 访问量:60

问:

我正在开发一个简单的 Python3 脚本,该脚本以 5 分钟为增量考虑数据。多亏了这篇文章,我有代码可以接受任何 Python 日期时间对象,然后将其四舍五入到最接近的五分钟。(:00、:05、:10、:15等)请注意,我不能使用 pandas。

现在,我需要能够将该“四舍五入”的日期时间与其他日期时间进行比较,在这里我遇到了一个问题。请考虑以下测试代码:

import sys
from datetime import datetime
from datetime import timedelta

def roundDownDateTime(dt):
    # Arguments:
    #   dt      datetime object
    delta = timedelta(minutes=1) * (dt.minute % 5)
    return dt - delta

def testAlarm(testDate):
    # Arguments:
    #   testDate    datetime object
    currDate = roundDownDateTime( datetime.now() )      # currDate is a DateTime object, rounded down to 5 mins
    print("currDate:  "+currDate.strftime("%Y%m%d%H%M"))
    print("testDate:  "+testDate.strftime("%Y%m%d%H%M"))
    if(currDate == testDate):
        print("ALARM!!!!")

def main():
    testDate = datetime.strptime(sys.argv[1], "%Y%m%d%H%M")
    testAlarm(testDate)

if __name__ == "__main__":
    main()

该代码执行以下所有操作:

  • 该函数采用您在命令行中输入的字符串, 然后将其转换为日期时间main()"%Y%m%d%H%M"
  • 您的日期时间将向下舍入到最后 5 分钟的增量
  • 在 中,您的日期将与当前日期进行比较,格式也四舍五入。testAlarm()"%Y%m%d%H%M"
  • 如果当前日期与 cmd 行参数匹配,则应在输出中得到一个。"ALARM!!!

这是实际输出,在我的 Ubuntu 机器上运行:

me@unbuntu1$ date
Tue Jan 17 14:27:41 UTC 2023
me@unbuntu1$ 
me@unbuntu1$ python3 toy04.py 202301171425
currDate:  202301171425
testDate:  202301171425
me@unbuntu1$

好的:尽管我正在向下舍入我的日期以匹配当前日期的“向下舍入”版本,但代码行的计算结果仍为 .虽然两个日期时间在格式上看起来相等,但它们在某种程度上并不相等。if(currDate == testDate):False"%Y%m%d%H%M"

我的第一个想法是,即使在四舍五入部分之后,“四舍五入”的日期时间仍然保留一些剩余的秒或微秒?所以我把我的函数修改为:

def roundDownDateTime(dt):
    # Arguments:
    #   dt      DateTime object
    delta = timedelta(minutes=1) * (dt.minute % 5)
    dt = dt - delta
    dt.replace(second=0, microsecond=0)
    return dt

但这并没有什么区别;我仍然得到与以前完全相同的输出。

通常,您只会出于警报目的而关心。但就我而言,我必须能够在其中一个(或多个)日期时间通过该函数后比较日期时间是否相等。我错过了什么?我的功能有问题吗?谢谢。currDate > testDateroundDownDateTime()roundDownDateTime()

python-3.x 日期时间 相等

评论

1赞 mousetail 1/17/2023
这很可能是浮点舍入错误
3赞 matszwecja 1/17/2023
docs.python.org/3/library/datetime.html#datetime-objects - 检查其中一个是否不幼稚。根据文档的说法,“对于相等性比较,朴素的实例永远不会等同于有意识的实例。
2赞 It_is_Chris 1/17/2023
您正在打印 ,但比较 的 datetime 对象,由于小数点,它们不相等。strftimecurrDate
0赞 Pete 1/17/2023
@It_is_Chris 这是一个很好的观点,可能是我困惑的根源。我想知道打印日期时间的推荐方法是什么?

答:

4赞 chepner 1/17/2023 #1

dt.replace返回一个新对象;它不会就地修改。datetimedt

def roundDownDateTime(dt):
    # Arguments:
    #   dt      DateTime object
    delta = timedelta(minutes=1) * (dt.minute % 5)
    dt = dt - delta
    return dt.replace(second=0, microsecond=0)