首页 文章

Python中的ISO时间(ISO 8601)

提问于
浏览
173

我有一个文件 . 在Python中,我想花费它的创建时间,并将其转换为ISO time (ISO 8601) string while preserving the fact that it was created in the Eastern Time Zone (ET) .

如何获取文件的ctime并将其转换为指示东部时区的ISO时间字符串(并在必要时考虑夏令时)?

11 回答

  • -5

    ISO 8601本地:

    import datetime
    datetime.datetime.now().isoformat()
    

    UTC至ISO 8601:

    import datetime
    datetime.datetime.utcnow().isoformat()
    

    本地到ISO 8601没有微秒:

    import datetime
    datetime.datetime.now().replace(microsecond=0).isoformat()
    

    带有TimeZone信息的UTC到ISO 8601(Python 3):

    import datetime
    datetime.datetime.utcnow().replace(tzinfo=datetime.timezone.utc).isoformat()
    

    带有TimeZone信息的本地ISO 8601(Python 3):

    import datetime, time
    
    # Calculate the offset taking into account daylight saving time
    utc_offset_sec = time.altzone if time.localtime().tm_isdst else time.timezone
    utc_offset = datetime.timedelta(seconds=-utc_offset_sec)
    datetime.datetime.now().replace(tzinfo=datetime.timezone(offset=utc_offset)).isoformat()
    

    对于Python 2,请参阅并使用pytz .

  • 30

    我在the documentation找到了datetime.isoformat . 它似乎做你想要的:

    datetime.isoformat([sep])
    
    Return a string representing the date and time in ISO 8601 format, YYYY-MM-DDTHH:MM:SS.mmmmmm or, if microsecond is 0, YYYY-MM-DDTHH:MM:SS
    
    If utcoffset() does not return None, a 6-character string is appended, giving the UTC offset in (signed) hours and minutes: YYYY-MM-DDTHH:MM:SS.mmmmmm+HH:MM or, if microsecond is 0 YYYY-MM-DDTHH:MM:SS+HH:MM
    
    The optional argument sep (default 'T') is a one-character separator, placed between the date and time portions of the result. For example,
    >>>
    
    >>> from datetime import tzinfo, timedelta, datetime
    >>> class TZ(tzinfo):
    ...     def utcoffset(self, dt): return timedelta(minutes=-399)
    ...
    >>> datetime(2002, 12, 25, tzinfo=TZ()).isoformat(' ')
    '2002-12-25 00:00:00-06:39'
    
  • 2

    ISO 8601 Time Representation

    国际标准ISO 8601描述了日期和时间的字符串表示 . 这种格式的两个简单例子是

    2010-12-16 17:22:15
    20101216T172215
    

    (两者均代表2010年12月16日),但格式也允许亚秒级分辨率时间并指定时区 . 这种格式当然不是特定于Python的,但它适合以便携式格式存储日期和时间 . 有关此格式的详细信息,请参见Markus Kuhn entry .

    我建议使用此格式在文件中存储时间 .

    在此表示中获取当前时间的一种方法是使用Python标准库中time模块的strftime:

    >>> from time import strftime
    >>> strftime("%Y-%m-%d %H:%M:%S")
    '2010-03-03 21:16:45'
    

    您可以使用datetime类的strptime构造函数:

    >>> from datetime import datetime
    >>> datetime.strptime("2010-06-04 21:08:12", "%Y-%m-%d %H:%M:%S")
    datetime.datetime(2010, 6, 4, 21, 8, 12)
    

    最强大的是Egenix mxDateTime模块:

    >>> from mx.DateTime.ISO import ParseDateTimeUTC
    >>> from datetime import datetime
    >>> x = ParseDateTimeUTC("2010-06-04 21:08:12")
    >>> datetime.fromtimestamp(x)
    datetime.datetime(2010, 3, 6, 21, 8, 12)
    

    References

  • 264

    这是我用来转换为XSD日期时间格式的内容:

    from datetime import datetime
    datetime.now().replace(microsecond=0).isoformat()
    # You get your ISO string
    

    在查找XSD日期时间格式( xs:dateTime )时,我遇到了这个问题 . 我需要从 isoformat 中删除微秒 .

  • 44

    ISO 8601 time format不存储时区名称,仅保留相应的UTC偏移量 .

    要将文件ctime转换为ISO 8601时间字符串,同时在Python 3中保留UTC偏移量:

    >>> import os
    >>> from datetime import datetime, timezone
    >>> ts = os.path.getctime(some_file)
    >>> dt = datetime.fromtimestamp(ts, timezone.utc)
    >>> dt.astimezone().isoformat()
    '2015-11-27T00:29:06.839600-05:00'
    

    该代码假定您的本地时区为Eastern Time Zone(ET),并且您的系统为给定的POSIX时间戳( ts )提供了正确的UTC偏移量,即,Python可以访问系统上的历史时区数据库,或者时区具有相同的时区在给定日期的规则 .

    如果您需要便携式解决方案; use the pytz module提供对the tz database的访问:

    >>> import os
    >>> from datetime import datetime
    >>> import pytz  # pip install pytz
    >>> ts = os.path.getctime(some_file)
    >>> dt = datetime.fromtimestamp(ts, pytz.timezone('America/New_York'))
    >>> dt.isoformat()
    '2015-11-27T00:29:06.839600-05:00'
    

    在这种情况下结果是相同的 .

    如果您需要时区名称/缩写/区域ID,请单独存储 .

    >>> dt.astimezone().strftime('%Y-%m-%d %H:%M:%S%z (%Z)')
    '2015-11-27 00:29:06-0500 (EST)'
    

    注意:否,UTC偏移中的 :EST 时区缩写不是ISO 8601时间格式的一部分 . 它不是唯一的 .

    同一库的不同库/不同版本可以对同一日期/时区使用不同的时区规则 . 如果是未来日期,则规则可能尚未知晓 . 换句话说,相同的UTC时间可能对应于不同的本地时间,具体取决于您使用的规则 - 以ISO 8601格式保存时间可保留UTC时间以及与您平台上使用的当前时区规则相对应的本地时间 . 如果具有不同的规则,您可能需要在不同的平台上重新计算本地时间 .

  • 42

    您需要使用 os.stat 来获取文件创建时间以及 time.strftimetime.timezone 的组合以进行格式化:

    >>> import time
    >>> import os
    >>> t = os.stat('C:/Path/To/File.txt').st_ctime
    >>> t = time.localtime(t)
    >>> formatted = time.strftime('%Y-%m-%d %H:%M:%S', t)
    >>> tz = str.format('{0:+06.2f}', float(time.timezone) / 3600)
    >>> final = formatted + tz
    >>> 
    >>> final
    '2008-11-24 14:46:08-02.00'
    
  • 14

    如果我错了(我不是),请纠正我,但UTC的偏移会随着夏令时而变化 . 所以你应该使用

    tz = str.format('{0:+06.2f}', float(time.altzone) / 3600)
    

    我也相信标志应该是不同的:

    tz = str.format('{0:+06.2f}', -float(time.altzone) / 3600)
    

    我错了,但我不这么认为 .

  • 10

    我同意Jarek,而且我还注意到ISO偏移分隔符是一个冒号,所以我认为最终的答案应该是:

    isodate.datetime_isoformat(datetime.datetime.now()) + str.format('{0:+06.2f}', -float(time.timezone) / 3600).replace('.', ':')
    
  • 4

    ISO 8601允许紧凑的表示,除了 T 之外没有分隔符,所以我喜欢使用这个单行来获取快速时间戳字符串:

    >>> datetime.datetime.utcnow().strftime("%Y%m%dT%H%M%S.%fZ")
    '20180905T140903.591680Z'
    

    如果您不需要微秒,请忽略 .%f 部分:

    >>> datetime.datetime.utcnow().strftime("%Y%m%dT%H%M%SZ")
    '20180905T140903Z'
    

    当地时间:

    >>> datetime.datetime.now().strftime("%Y%m%dT%H%M%S")
    '20180905T140903'
    
  • 2

    我开发了这个功能:

    def iso_8601_format(dt):
        """YYYY-MM-DDThh:mm:ssTZD (1997-07-16T19:20:30-03:00)"""
    
        if dt is None:
            return ""
    
        fmt_datetime = dt.strftime('%Y-%m-%dT%H:%M:%S')
        tz = dt.utcoffset()
        if tz is None:
            fmt_timezone = "+00:00"
        else:
            fmt_timezone = str.format('{0:+06.2f}', float(tz.total_seconds() / 3600))
    
        return fmt_datetime + fmt_timezone
    
  • 0
    import datetime, time    
    def convert_enddate_to_seconds(self, ts):
        """Takes ISO 8601 format(string) and converts into epoch time."""
         dt = datetime.datetime.strptime(ts[:-7],'%Y-%m-%dT%H:%M:%S.%f')+\
                    datetime.timedelta(hours=int(ts[-5:-3]),
                    minutes=int(ts[-2:]))*int(ts[-6:-5]+'1')
        seconds = time.mktime(dt.timetuple()) + dt.microsecond/1000000.0
        return seconds 
    
    >>> import datetime, time
    >>> ts = '2012-09-30T15:31:50.262-08:00'
    >>> dt = datetime.datetime.strptime(ts[:-7],'%Y-%m-%dT%H:%M:%S.%f')+ datetime.timedelta(hours=int(ts[-5:-3]), minutes=int(ts[-2:]))*int(ts[-6:-5]+'1')
    >>> seconds = time.mktime(dt.timetuple()) + dt.microsecond/1000000.0
    >>> seconds
    1348990310.26
    

相关问题