Python 基础 (标准库):time (时间的访问和转换)

1. 官方文档

time --- 时间的访问和转换 — Python 3.12.2 文档

2. 准备知识

协调世界时 UTC (Coordinated Universal Time)

协调世界时(Coordinated Universal Time,UTC),是一种国际标准的时间表示方式。UTC 是以原子钟为基础,以地球自转为参考,通过国际协调来确保全球的时间同步。UTC 的单位是秒,它是世界上所有标准时间的基准,也是全球通用的标准时间。

接下来,介绍一下闰秒的概念。由于地球自转的速度不稳定,UTC 与地球自转周期之间的差异会逐渐累积。闰秒(Leap second)是指为了补偿地球自转减慢而添加到协调世界时中的一个插入的秒,以保持协调世界时与太阳时间同步。国际地球自转与参考系统服务(International Earth Rotation and Reference Systems Service,IERS)会根据需要,在 UTC 中插入或删除闰秒。闰秒的插入或删除通常在每年的6月或12月进行,但并不是每年都需要进行调整。

时区 Time Zone/当地时间 Local time

时区是指地球上不同地区所采用的时间,各个时区的时间都是相对于 UTC 而言的,即 UTC+时差=当地时间。比如,北美和南美属于 Central Time Zone(CT),比 UTC 晚5或6小时(当地时间晚,所以是减),使用 UTC-5:00 或 UTC-6:00 表示;澳大利亚悉尼属于 Australian Eastern Time Zone(AET),比 UTC 早10或11个小时,表示为 UTC+10:00 或 UTC+11:00。注意,-5:00 和 +11:00 对应夏令时,夏令时的概念将在下一小节介绍。

对于英语为母语者,可能会认为 “协调世界时” 的缩写应该是 CUT 而不是 UTC;对于法语为母语者,可能更习惯的叫法是 “Temps universsel coordonnnel”,对应缩写 TUC。国际电信联盟和国际天文学联盟规定,将 UTC 作为官方缩写,无论何种语言,缩写都是 UTC。

夏令时 DST (Daylight Saving Time)

夏令时是一种为了充分利用光照资源而人为调整地方时间的制度。夏季日照时间通常比冬季更长,为了充分利用光照资源,节约照明用电,一些地区在春季和夏季实行夏令时(或称夏时制、日光节约时制,daylight savings time,DST)。

在实行夏令时的地方,时钟将在春天开始时,被调快一个小时(实际上少了一个小时);在秋天,被重置为标准时间。通常在当地时间凌晨2点进行调整,也就是说,在春天,从凌晨2点到凌晨2点59分的时间不存在;而在秋天,从凌晨1点到凌晨1点59分的时间会发生两次。

夏令时的规则也是可能变化的,比如,在美国和加拿大,2007年之前,时钟在4月的第一个星期日调快一小时,在10月的最后一个星期日调慢一小时;2007年之后,时钟在3月的第二个星期日调快一小时,在11月的第一个星期日调慢一小时。

用字母 S 和 D 分别代表时区表示法中的标准时间和夏令时,如:Central Standard Time (CST)
Australian Eastern Daylight Time (AEDT)。

历元 Epoch

在计算机科学中,epoch 是一个常用的术语,它通常指的是一个历元,即一个起始时间点,所有的计算机时间都是从这个时间点开始计算的。

概括来说,历元就是测算时间流逝的起点。Windows 和大多数 UNIX 系统上定义的 epoch 都是: 1970-01-01, 00:00:00(UTC)

1970-01-01 (UTC)是一个常见的历元,但它并不是计算机领域的唯一历元。事实上,不同的操作系统、文件系统和 api 有可能使用不同的历元。如,UNIX 系统将 epoch 定义为1970年1月1日,Win32 API 将 epoch 定义为1601年1月1日。

3. 时间表示法

3.1 浮点数:从某个起始时间点(epoch)开始所经过的秒数

在Python时间概念中,一种表示方法是,使用一个浮点数,该浮点数表示自某个历元以来所经过的秒数(历元的含义如前所述,默认为 1970-01-01, 00:00:00 UTC)。由于 epoch 在定义时,使用的是 UTC,当前时刻从 epoch 开始经过的秒数是不会随地理位置的变化而变化的。

1970-01-02, 00:00:00(UTC),可以记为86400,表示距离 epoch 86400秒,因为一分钟有60秒,一小时有60分钟,一天有24小时,1970年1月2日只比历元晚一天,60*60*24 = 86400。另外,可以用负数的秒数表示历元之前的时间,比如,1970-12-31, 00:00:00(UTC),可表示为 -86400秒。

python 中,可以使用 time.gmtime(0) 来获取系统历元,返回的数据类型为 struct_time(time.gmtime() 和 struct_time 的用法将在后文介绍);可以使用 time.time() 返回自 epoch 到现在经过的秒数(带小数的秒 fractional seconds)。

<1> time.time() → float:返回浮点数,表示从 epoch 到现在经历的秒数。

  1. 用秒数来表示时间是有用的,原因如下:(1)可以使用浮点数来计算两个时间点之间的差值。(2)浮点数很容易序列化,便于存储并进行无损的数据传输。
  2. 在 Windows 和大多数 Unix 系统中,闰秒不会被计入从 epoch 开始的秒数形式的时间中,这种情况通常被称为 Unix Time。
  3. 需要注意的是,此函数返回值总是浮点数,但并非所有系统都能提供高于1秒的精度。
  4. 通常情况下,多次调用此函数,返回值序列非递减,但如果在两次调用之间修改了系统时钟,则有可能返回比先前调用更低的值。
  5. 返回的浮点数字可以通过将其传递给 gmtime() 函数获得 UTC,或传递给 localtime() 函数获得本地时间(这两种函数都返回 struct_time 对象)。

012915ad178840b9b9ad95e691ce2889.png

<2> time.time_ns() → int:返回整数,表示从 epoch 到现在所经历的纳秒数。

使用time_ns() 能够避免 float 类型导致的精度损失。

2cc2288f4311429f96f102a11acda657.png

3.2 字符串(时间戳 timestamp)

有时候,我们希望看到以字符串形式表示的时间信息(也称为时间戳,timestamp),对此,可以使用 time.ctime(),将 Python 浮点数时间(自 epoch 以来经过的秒数)转换为字符串。

<3> time.ctime([secs]):将由距 epoch secs 秒表示的时间转换为以下形式的字符串:'Sat Mar 2 12:05:27 2024',字符串内容对应本地时间。

ff29543776264e1e86aee3532f65c38a.png

  1. 若未提供 secs,或 secs 为 None,secs 默认使用 time.time() 返回的当前时间。
  2. 日期字段的长度为两个字符,如果日期只有一位数字,会以空格填充。
  3. time.ctime(secs) 等价于 asctime(time.localtime(secs)) ,asctime 和 localtime 的含义将在后文介绍。
  4. ctime() 返回的是的字符串是本地时间,依赖于地理位置(时区)。不过,区域设置信息是可以在计算机的设置中修改的,无需实际搬迁。
  5. ctime 不考虑语言环境信息(locale information),locale information 指的是系统或应用程序使用的语言或地区设置。在不同的系统或应用中,呈现日期、文本等信息时,采用的格式可能有差异,如字符串中元素的顺序,以及日和月的缩写等,但ctime() 不考虑这些。
time.ctime(0)  # epoch

# 未提供secs,默认使用time.time()
time.ctime()   
# 'Thu Jan  1 08:00:00 1970'

t = time.time()
# 'Sat Mar  2 18:15:04 2024'
time.ctime(t)
# 'Sat Mar  2 18:15:04 2024'

3.3 元组

除了可以用数字和字符串表示 Python 时间,还可以使用另一种基本数据结构:元组。使用元组表示的时间具有更好的可读性。

用元组表示时间时,元组中应含有9个元素,每个位置都有特性含义,对应特定的时间元素:

66282a819aef45ee80a8178b2cc11a4b.png

一个用元组表示时间的示例:

62a9b625f96d4c5a807e6af5fe877ee0.png

3.4 对象 struct_time

相比与单个的、基于秒的数字,元组已经将信息很好的组织起来了,但看起来仍然是一堆数字。为此,考虑引入 struct_time 对象,更高效的组织时间数据。

struct_time 其实是元组的一个子类,他通过使用 Python 的 collections 模块中的 NamedTuple,将元组的数字序列与对应的标识符关联起来。位置与属性的具体关系如下(前9个与元组部分相同,新增了 tm_zone 和 tm_gmtoff)。

索引属性
0tm_year(例如,1993)
1tm_monrange [1, 12]
2tm_dayrange [1, 31]
3tm_hourrange [0, 23]
4tm_minrange [0, 59]
5tm_secrange [0, 61]
6tm_wday取值范围 [0, 6];周一为 0
7tm_ydayrange [1, 366]
8tm_isdst0, 1 或 -1;如下所示
N/Atm_zone时区名称的缩写
N/Atm_gmtoff以秒为单位的UTC以东偏离

struct_time 这个名字其实来自于 C 的 time 库,事实上,struct_time 对象的实现是基于 C 语言的 time.h 头文件中的 tm 结构体。在 Python 中,struct_time 对象是通过将 C 语言中的 tm 结构体转换为Python 中的元组来实现的。

  1. struct_time 除了在可读性和可用性方面更具优势外,它也是 Python time 模块中许多函数的返回值类型,比如,函数 time.localtime() 返回的是 struct_time 类型的当前本地时间;函数 time.gmtime() 返回的是 struct_time 类型的当前 UTC;这两个方法也可以接收参数 secs,将秒表示的时间转换为 struct_time 类型的数据,具体细节参见 <3.1>。
  2. struct_time 的元素可以通过索引或属性名访问。可以注意一下以下几个属性:tm_zone,表示对应的时区;tm_gmtoff,表示 UTC offset;tm_isdst:表示是否是夏令时。如果表示的是 UTC,UTC 从不使用夏令时,返回结果中 isdst 标志为0,tm_zone 和 tm_gmtoff 分别为 UTM 和 0。

使用 time 模块中的函数获得 struct_time 数据

import time

# ==========================================================
t = time.localtime()

print([item for item in dir(t) if not item.startswith('_')])
# ['count', 'index', 'n_fields', 'n_sequence_fields', 'n_unnamed_fields', 
# 'tm_gmtoff', 'tm_hour', 'tm_isdst', 'tm_mday', 'tm_min', 'tm_mon', 
# 'tm_sec', 'tm_wday', 'tm_yday', 'tm_year', 'tm_zone']
t.tm_year  
# 2024
t.tm_mon
# 3
t.tm_mday
# 2
t.tm_zone
# '中国标准时间'
t.tm_gmtoff
# 28800
t.tm_isdst
# 0
print(28800//3600)
# 8 UTC+8:00

# ==========================================================
t = time.gmtime()

t.tm_zone
# 'UTC'
t.tm_gmtoff
# 0
t.tm_isdst
# 0

使用元组获得 struct_time 数据

注意:使用元组作为入参时,必须保证至少有9个元素。84471beb662d4b58bc317081744c447d.png

如果只传入9个数据,zone 和 gmtoff 信息都为 None。

6ab0fece10684357aa37a44ef9f53a73.png

总结一下,我们目前能用以下几种方法获取当前时间:time.time(),time.time_ns(),time.ctime(),time.gmtime(),time.localtime()。

4. 不同时间表示法之间互相转换

4.1 秒表示法 -> struct_time表示法

从 epoch 开始经过的秒数不会随地理位置的变化而变化,然而,在将此时间改为其他形式(字符串、struct_time)时,要区分转换为 UTC 还是 Localtime(前文已经介绍了ctime(),用于转换为Localtime 字符串)。

<4> time.gmtime([secs]):将以自 epoch 以来 secs 秒的时间转换为 UTC。 

  1. 若未提供 secs 或 secs 为 None,secs 默认使用 time.time() 返回的当前时间。
  2. 秒数的小数部分将被忽略,gmtime(1.99) 和 gmtime(1) 返回结果相同。
  3. secs 为0时,返回值即为 epoch(UTC,struct_time 对象)。 
  4. UTC 从不使用夏令时,使用 gmtime() 返回的结果 isdst 标志将始终为0。
# epoch
time.gmtime(0)
# time.struct_time(tm_year=1970, tm_mon=1, tm_mday=1, tm_hour=0, tm_min=0, tm_sec=0, tm_wday=3, tm_yday=1, tm_isdst=0)

# 当前UTM时间
t = time.time()
time.gmtime(t)
# time.struct_time(tm_year=2024, tm_mon=3, tm_mday=2, tm_hour=10, tm_min=9, tm_sec=38, tm_wday=5, tm_yday=62, tm_isdst=0)
time.gmtime()
# time.struct_time(tm_year=2024, tm_mon=3, tm_mday=2, tm_hour=10, tm_min=9, tm_sec=38, tm_wday=5, tm_yday=62, tm_isdst=0)

# gmtime忽略秒中的小数部分
time.gmtime(1)
# time.struct_time(tm_year=1970, tm_mon=1, tm_mday=1, tm_hour=0, tm_min=0, tm_sec=1, tm_wday=3, tm_yday=1, tm_isdst=0)
time.gmtime(1.99)
# time.struct_time(tm_year=1970, tm_mon=1, tm_mday=1, tm_hour=0, tm_min=0, tm_sec=1, tm_wday=3, tm_yday=1, tm_isdst=0)

<5> time.localtime([secs]):与 gmtime() 相似,但转换为当地时间。

  1. 若未提供 secs 或 secs 为 None,secs 默认使用 time.time() 返回的当前时间。
  2. 给定地区的时间采用了夏令时(DST)时,dst 标志设置为 1。
  3. 如果传递给该函数的时间戳超出了 struct_time 对象能表示的范围,会导致 OverflowError 异常。 具体来说,对于 32 位系统,struct_time 对象对应年份范围是 1970 到 2038 年,因为在 32 位系统中,时间戳是以秒为单位存储的,而 2038 年 1 月 19 日 03:14:07 是 32 位系统能够表示的最大时间戳(2^31-1=2147483647),如果在 32 位系统上使用 time.localtime(2147483648),就会抛出 OverflowError 异常。

注意对比 time.localtime() 与 time.gmtime() 的差异(当前时区为 UTC+8:00)。

time.gmtime(0)
# time.struct_time(tm_year=1970, tm_mon=1, tm_mday=1, tm_hour=0, tm_min=0, tm_sec=0, tm_wday=3, tm_yday=1, tm_isdst=0)

time.localtime(0)
# time.struct_time(tm_year=1970, tm_mon=1, tm_mday=1, tm_hour=8, tm_min=0, tm_sec=0, tm_wday=3, tm_yday=1, tm_isdst=0)

4.2  struct_time表示法 -> 秒表示法

 <6> calender.timegm(t):gmtime() 的反函数。

time.gmtime() 函数在 time 库中没有对应的逆函数,必须使用 Python 的 calender 模块中的 timegm() 的函数。calender.timegm 接受 struct_time 或元组,返回自 epoch 以来的秒数。

import time
import calendar

t = time.time()
t_struct_time = time.gmtime(t)
t_back = calendar.timegm(t_struct_time)

print(t)
# 1709374320.2391047
print(t_struct_time)
# time.struct_time(tm_year=2024, tm_mon=3, tm_mday=2, tm_hour=10, tm_min=12, tm_sec=0, tm_wday=5, tm_yday=62, tm_isdst=0)
print(t_back)
# 1709374320
print(type(t_back))
# <class 'int'>

<7> time.mktime(t):localtime() 的反函数。

不同于 gmtime(),Python 的 time 模块中存在 localtime() 的反函数:mktime()。

  1. t 为 struct_time 或者至少9个元素的元组(因为需要 dst 标志;如果不清楚 dst,使用 -1 作为 dst 标志)。
  2. t 应表示 Local time,而不是 UTC ;
  3. 返回浮点数,以便与 time() 兼容。
  4. 如果输入值不能表示为有效时间,则触发 Overflow 或 ValueError,这取决于Python或底层C库是否捕获到无效值。
  5. 一定要要记住,mktime 需要使用本地时间。举一个使用不当的例子:假设当前时区为中国标准时间(UTC+8:00),使用不带参数的 time.gmtime() 返回当前时间:2024年3月4日3:9:34(UTC),对应 2024年3月4日11:9:34(中国标准时间)。然后,把 gmtime() 的结果直接传递给 mktime() 返回秒数,mktime() 将假设你的意思是 2024年3月4日3:9:34(中国标准时间),对应 UTC 2024年3月3日19:9:34。最后,使用 gmtime() 和 localtime() 将这些秒转换回 UTC 和本地时间,得到 UTC 将比真正的 UTC 晚8小时,得到的本地时间也同理,比真正的本地时间晚8小时。
from time import gmtime, mktime

current_utc = time.gmtime()
current_utc_secs = mktime(current_utc)
time.gmtime(current_utc_secs)     # 值错误
time.localtime(current_utc_secs)  # 值错误
# time.struct_time(tm_year=2024, tm_mon=3, tm_mday=3, tm_hour=19, tm_min=20, tm_sec=40, tm_wday=6, tm_yday=63, tm_isdst=0)
# time.struct_time(tm_year=2024, tm_mon=3, tm_mday=4, tm_hour=3, tm_min=20, tm_sec=40, tm_wday=0, tm_yday=64, tm_isdst=0)

current_local = time.localtime()
current_local_secs = mktime(current_local)
time.gmtime(current_local_secs)     # 值正确
time.localtime(current_local_secs)  # 值正确
# time.struct_time(tm_year=2024, tm_mon=3, tm_mday=4, tm_hour=3, tm_min=20, tm_sec=40, tm_wday=0, tm_yday=64, tm_isdst=0)
# time.struct_time(tm_year=2024, tm_mon=3, tm_mday=4, tm_hour=11, tm_min=20, tm_sec=40, tm_wday=0, tm_yday=64, tm_isdst=0)

总结(与以秒表示的时间相关的函数总结)

函数

入参

返回值

time.gmtime(secs)

自历元以来的秒数(浮点数或整数)

参数为 None 或无参数时,secs = time.time()

UTC(struct_time)

time.localtime(secs)

自历元以来的秒数(浮点数或整数)

参数为 None 或无参数时,secs = time.time()

本地时间(struct_time)

calender.timegm()

UTC(struct_time)

自历元以来的秒数(整数)

time.mktime()

本地时间(struct_time)

自历元以来的秒数(浮点数)

4.3 struct-time表示法 -> 字符串表示法

Python.time 模块中,有两个函数可用于将struct_time对象转换为字符串:

  • asctime ()
  • strftime ()

<8> time.asctime([t]):将元组或由 struct_time 表示的时间(如 gmtime() 或 localtime() 的返回值)转换为以下形式的字符串:'Mon Mar 4 11:50:41 2024',日期字段的长度为两个字符,如果日期只有一个数字则会以零填充。

  1. 若未提供 t ,t 默认使用由 localtime() 返回的当前时间。
  2. asctime() 的工作方式类似于前面介绍的 ctime(),只不过传递的不是浮点数,而是元组,这两个函数的时间戳格式也是相同的,且都不适用区域设置信息(ignore locale information)。
  3. asctime() 最大的缺点是它的格式不灵活。strftime() 允许格式化时间戳,能够解决这个问题。
from time import strftime, localtime

time.asctime()
# 'Mon Mar  4 14:34:22 2024'

import locale
# 获取默认时区
current_locale = locale.getlocale()

# 修改时区
locale.setlocale(locale.LC_TIME, 'en_US.UTF-8')  # Chinese - Hong Kong
time.asctime()
# 'Mon Mar  4 14:34:22 2024'

# 恢复默认时区
locale.setlocale(locale.LC_TIME, current_locale)

<9> time.strftime(format[, t]):将元组或由 struct_time 表示的时间(如 gmtime() 或 localtime() 的返回值)转换到由 format 参数指定的字符串。format 必须是一个字符串。

  1. strftime(),代表 string format time(“字符串格式时间”)。
  2. strftime() 接受两个参数:format 和 t。
  3. format 用于指定字符串中各种时间元素的顺序和形式,格式化字符串中可以使用指示符(Directive,以%开头的字符序列,用来指定特定的时间元素,例如: %d:星期几,%m:月份,%Y:年;也可以使用指示符以外的自定义文本内容
  4. t 可选,为一个元组或 struct_time。若未提供 t ,t 默认使用由 localtime() 返回的当前时间;如果 t 中的任何字段超出允许范围,引发ValueError。
time.strftime('%Y-%m-%d')
# '2024-03-04'
time.strftime('当前时间:%Y-%m-%d')  # format中含有自定义文本内容
# '当前时间:2024-03-04'

# 可以了解一下 datetime模块,提供了用于处理日期和时间的更快捷的框架
from datetime import date
date(year=2019, month=3, day=4).isoformat()
# '2019-03-04'

list of directives:

指令含意
%a本地化的缩写星期中每日的名称。
%A本地化的星期中每日的完整名称。
%b本地化的月缩写名称。
%B本地化的月完整名称。
%c本地化的适当日期和时间表示。
%x本地化的适当日期表示。
%X本地化的适当时间表示。
%p本地化的 AM 或 PM 。
%Y十进制数表示的带世纪的年份。
%m十进制数 [01,12] 表示的月。
%d十进制数 [01,31] 表示的月中日。
%H十进制数 [00,23] 表示的小时(24小时制)。
%I十进制数 [01,12] 表示的小时(12小时制)。
%M十进制数 [00,59] 表示的分钟。
%S十进制数 [00,61] 表示的秒。
%f十进制表示的的微秒数 [000000,999999]。
%w十进制数 [0(星期日),6] 表示的周中日。
%j十进制数 [001,366] 表示的年中日。
%U十进制数 [00,53] 表示的一年中的周数(星期日作为一周的第一天)。 在第一个星期日之前的新年中的所有日子都被认为是在第 0 周。
%W十进制数 [00,53] 表示的一年中的周数(星期一作为一周的第一天)。 在第一个星期一之前的新年中的所有日子被认为是在第 0 周。
%y十进制数 [00,99] 表示的没有世纪的年份。
%z时区偏移以格式 +HHMM 或 -HHMM 形式的 UTC/GMT 的正或负时差指示,其中H表示十进制小时数字,M表示小数分钟数字 [-23:59, +23:59] 
%%字面的 '%' 字符。

(1) 不同于 asctime 输出的格式固定,strftime 能够利用区域信息(Local Information)。

asctime 版本,字符串格式固定,参考 <3.3 -8 代码示例>。

strftime 版本,可以按照对应时区的语言风格输出字符串:

from time import strftime, localtime

strftime('%a, %A, %b, %B, %c, %x, %X')
# '周一, 星期一, 3月, 三月, 2024/3/4 14:31:19, 2024/3/4, 14:31:19'

import locale
# 获取默认时区
current_locale = locale.getlocale()

# 修改时区
locale.setlocale(locale.LC_TIME, 'en_US.UTF-8')  # Chinese - Hong Kong
strftime('%a, %A, %b, %B, %c, %x, %X')
# 'Mon, Monday, Mar, March, 3/4/2024 2:31:19 PM, 3/4/2024, 2:31:19 PM'

# 恢复默认时区
locale.setlocale(locale.LC_TIME, current_locale)

4.4 字符串表示法 -> struct-time表示法

可以使用 strptime() 将时间字符串转换为 struct_time。

<10> time.strptime(string[, format]):根据格式 format(默认为  '%a %b %d %H:%M:%S %Y')解析表示时间的字符串 string,返回 struct_time 对象 。

  1. strptime,代表 string parse time(字符串解析时间)
  2. strptime() 可以接收两个参数:string 和 format,都必须为字符串。的第一个参数是要转换的时间戳;第二个参数可选,表示时间戳的格式,默认为 '%a %b %d %H:%M:%S %Y',如果待转换的时间戳是这种格式,可以省略第2个参数。
  3.  如果 string 不能根据 format 来解析,或者解析后有多余的数据,会引发ValueError。
  4. struct_time有9个关键的日期和时间组件,strptime() 须要为那些不能从string中解析的元素提供默认值,用于填充任何缺失数据的默认值是 (1900, 1, 1, 0, 0, 0, 0, 1, -1)。tm_isdst=-1,表示 strptime()不能通过时间戳确定是否使用夏令时。 
  5. 一个小细节:如果使用 %I 指令来解析小时, %p 指令只影响输出小时字段(自动转换为24小时值的小时信息,参考下方第二个代码示例)。
time.strptime('2024-03-04', '%Y-%m-%d')
# time.struct_time(tm_year=2024, tm_mon=3, tm_mday=4, tm_hour=0, tm_min=0, tm_sec=0, tm_wday=0, tm_yday=64, tm_isdst=-1)

time.strftime('%a %b %d %H:%M:%S %Y')
# '周一 3月 04 14:55:30 2024'

time.strptime('周一 3月 04 14:55:30 2024')
# time.struct_time(tm_year=2024, tm_mon=3, tm_mday=4, tm_hour=14, tm_min=55, tm_sec=30, tm_wday=0, tm_yday=64, tm_isdst=-1)
time.strftime('%Y-%m-%d %I:%M:%S %p')
# '2024-03-04 03:28:38 下午'

time.strptime('2024-03-04 03:28:38 下午', '%Y-%m-%d %I:%M:%S %p')
# time.struct_time(tm_year=2024, tm_mon=3, tm_mday=4, tm_hour=15, tm_min=28, tm_sec=38, tm_wday=0, tm_yday=64, tm_isdst=-1)

4.5 秒表示法 <-> 字符串表示法

(1)秒表示法 -> 字符串表示法

需要返回当地时间时:

方法一(直接):参考 2.2 time.ctime(secs),返回本地时间。

方法二:先由 time.localtime(secs) 得本地时间 t -> 由 strftime(format, t) 得 format 格式的字符串。

需要返回UTC时:

先由 time.gmtime(secs) 得 UTC t -> 由 strftime(format, t) 得到 format 格式的字符串。

(2)字符串表示法 -> 秒表示法

字符串为当地时间时:字符串 -> 由 srtptime() 得 struct time t -> mktime(t)。

字符串为 UTC 时:字符串 -> 由 srtptime() 得 struct time t -> calende.timegm(t)。

5. 暂停运行

<11> time.sleep(secs):调用方线程暂停执行给定的秒数,该参数可以为浮点数以指定一个更精确的休眠时间。

暂停时间有可能比请求的要长出一段不确定的时间,因为会受系统中的其他活动排期影响。

  import logging

    logging_format = "%(asctime)s: %(message)s"
    logging.basicConfig(format=logging_format, level=logging.DEBUG, datefmt="%H:%M:%S")

    logging.info('Hello')
    time.sleep(2)
    logging.info('Bye')

 返回结果:

6. 衡量性能

<12> time.perf_counter() → float:返回一个性能计数器的值(以小数表示的秒为单位),即用于测量较短持续时间的具有最高有效精度的时钟。 它会包括睡眠状态所消耗的时间并且作用于全系统范围。 返回值的参考点未被定义,因此只有两次调用之间的差值才是有效的。

perf_counter 与 time.time() 的区别:

  • time.time() 返回自 1970 年 1 月 1 日以来的秒数,通常被用于计算时间戳。
  • time.perf_counter() 返回一个高精度的计时器,它包含了当前进程的 CPU 时间以及其他一些因素。它通常被用于计算程序的运行时间,而不是计算时间戳。
  • 在 Python 3.3 以前,time.time() 函数的精度是 1 秒,而 time.perf_counter() 函数的精度是 CPU 时钟周期级别的。在 Python 3.3 以后,time.time() 函数的精度也提高到了 CPU 时钟周期级别,但是 time.perf_counter() 函数仍然是最准确的计时器。 因此,如果你需要计算程序的运行时间,那么最好使用 time.perf_counter() 函数。如果你需要计算时间戳,那么就使用 time.time() 函数。
from time import perf_counter
def longrunning_function():
    for i in range(1, 11):
        time.sleep(i / i ** 2)

start = perf_counter()
longrunning_function()
end = perf_counter()
execution_time = (end - start)
execution_time
# 3.027007800003048

<13> time.perf_counter_ns() → int:与 time.perf_counter() 相似,但是返回时间为纳秒。

  • 21
    点赞
  • 13
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值