Python3 中的时间与日期模块详解
Python 中不包含表示日期和时间的基本数据类型,但是提供了如下三个模块用于操作时间日期类型的数据:
-
time
:提供与时间相关的功能。包含时钟时间、处理器运行时间、基本的格式化工具等 -
datetime
:提供处理时间日期的高级接口。如时间日期之间的算术计算和大小比较等 -
calendar
:提供类似日历的年、月、日、周的格式化输出和其他日历相关的功能
一、time
time
模块包含多种类型的“时钟”时间,方便处理多种不同需求的任务。如:
-
time()
返回自纪年以来的秒数。纪年指time.gmtime(0)
函数的返回值,大多数系统中是 1970年1月1日00:00:00(UTC) -
monotonic()
可以用来测量长时间运行的进程,它不会因为系统时间被修改而发生变化 -
perf_counter()
提供了精度最高的时间量度,因此多用于获取短时间段的高精度结果 -
process_time()
返回当前进程中系统和用户 CPU 时间的总和。不包括sleep()
时间
测试程序:
import textwrap
import time
available_clocks = [
('time', time.time),
('monotonic', time.monotonic),
('perf_counter', time.perf_counter),
('process_time', time.process_time),
]
for clock_name, func in available_clocks:
print(textwrap.dedent('''\
{name}:
adjustable : {info.adjustable}
implementation: {info.implementation}
monotonic : {info.monotonic}
resolution : {info.resolution}
result : {result}
''').format(
name=clock_name,
info=time.get_clock_info(clock_name),
result=func())
)
输出中包含了各时钟函数的实现方式、精度和执行结果等:
time:
adjustable : True
implementation: clock_gettime(CLOCK_REALTIME)
monotonic : False
resolution : 1e-09
result : 1576935284.1307783
monotonic:
adjustable : False
implementation: clock_gettime(CLOCK_MONOTONIC)
monotonic : True
resolution : 1e-09
result : 1653915.765674168
perf_counter:
adjustable : False
implementation: clock_gettime(CLOCK_MONOTONIC)
monotonic : True
resolution : 1e-09
result : 1653915.765707337
process_time:
adjustable : False
implementation: clock_gettime(CLOCK_PROCESS_CPUTIME_ID)
monotonic : True
resolution : 1e-09
result : 0.017164144
上述几个时钟函数中,只有 time.time()
在计算时间时有明确的参考点(time.gmtime(0)
),另外三个函数都没有定义绝对的起点作为基准,因此常用来计算某个过程耗费的时间总和(多次执行并计算时间差),而无法获取一个标准的绝对时间。
>>> start = time.perf_counter()
>>> end = time.perf_counter()
>>> end - start
8.590425299999993
上述函数返回的都是以秒为单位精度较高的浮点数。对于需要记录或者打印方便阅读的时间日期时,可以使用 ctime()
函数:
>>> time.ctime()
'Sat Dec 21 21:56:41 2019'
>>> later = time.time() + 30
>>> time.ctime(later)
'Sat Dec 21 21:57:19 2019'
time
模块中还定义了 struct_time
结构用来表示日期和时间中的每一项独立的值(年月日、时分秒等)。
>>> loc_time = time.localtime()
>>> loc_time
time.struct_time(tm_year=2019, tm_mon=12, tm_mday=21, tm_hour=22, tm_min=20, tm_sec=32, tm_wday=5, tm_yday=355, tm_isdst=0)
>>> loc_time.tm_year
2019
>>> loc_time.tm_hour
22
时间的格式化输出
strftime()
函数可以用来将 struct_time
格式的时间值转换为字符串的形式表示。strptime()
函数的行为则相反。如:
>>> import time
>>> loc_time = time.localtime()
>>> loc_time
time.struct_time(tm_year=2019, tm_mon=12, tm_mday=21, tm_hour=23, tm_min=21, tm_sec=33, tm_wday=5, tm_yday=355, tm_isdst=0)
>>> time.strftime('%Y-%m-%d %H:%M:%S', loc_time)
'2019-12-21 23:21:33'
>>> now = time.ctime()
>>> now
'Sat Dec 21 23:23:31 2019'
>>> time.strptime(now)
time.struct_time(tm_year=2019, tm_mon=12, tm_mday=21, tm_hour=23, tm_min=23, tm_sec=31, tm_wday=5, tm_yday=355, tm_isdst=-1)
常见的字符串形式的时间日期格式如下:
>>> time.strftime('%Y-%m-%d %H:%M:%S')
'2019-12-21 23:26:40'
>>> time.strftime('%a %b %d %H:%M:%S %Y')
'Sat Dec 21 23:27:15 2019'
strftime()
函数支持的更多格式定义可参考 help(time.strftime)
。
二、datetime
datetime 模块中定义的函数和类可以对日期和时间进行转换、格式化输出、算术计算等操作。
time
time 类可以表示包含时、分、秒、时区等信息的时间对象。
>>> import datetime
>>> t = datetime.time(1, 2, 3)
>>> print(t)
01:02:03
>>> t.hour
1
>>> t.minute
2
>>> t.second
3
>>> t.tzinfo
>>>
date
date 类可以表示包含年、月、日等信息的日期值。其 today()
方法可以获取当天的日期。
>>> from datetime import date
>>> today = date.today()
>>> today
datetime.date(2019, 12, 21)
>>> today.year
2019
>>> today.month
12
>>> today.day
21
datetime
datetime 模块中的 datetime
类可以表示完整的日期和时间,类似 time
类和 date
类的结合。
>>> import datetime
>>> now = datetime.datetime.now()
>>> now
datetime.datetime(2019, 12, 22, 0, 30, 21, 372631)
>>> print(now)
2019-12-22 00:30:21.372631
>>> t = datetime.time(1, 2, 3)
>>> print(t)
01:02:03
>>> d = datetime.date.today()
>>> print(d)
2019-12-22
>>> dt = datetime.datetime.combine(d, t)
>>> dt
datetime.datetime(2019, 12, 22, 1, 2, 3)
>>> print(dt)
2019-12-22 01:02:03
timedelta
timedelta
类可以表示某个特定长度的时间段(以年月日或时分秒等为单位)。
两个 datetime
相减会得到 timedelta
对象,也可以用 datetime
加上或者减去 timedelta
得到新的时间值。
日期加减:
>>> import datetime
>>> today = datetime.date.today()
>>> today
datetime.date(2019, 12, 22)
>>> twodays = datetime.timedelta(days=2)
>>> print(twodays)
2 days, 0:00:00
>>> today - twodays
datetime.date(2019, 12, 20)
时间加减:
>>> import datetime
>>> now = datetime.datetime.now()
>>> print(now)
2019-12-22 00:35:30.298198
>>> delta = datetime.timedelta(days=1, minutes=30)
>>> print(delta)
1 day, 0:30:00
>>> now - delta
datetime.datetime(2019, 12, 21, 0, 5, 30, 298198)
>>> print(now - delta)
2019-12-21 00:05:30.298198
比较大小
>>> t1 = datetime.time(12, 30, 20)
>>> print(t1)
12:30:20
>>> t2 = datetime.time(11, 20, 40)
>>> print(t2)
11:20:40
>>> t2 > t1
False
>>> today = datetime.date.today()
>>> print(today)
2019-12-22
>>> tomorrow = today + datetime.timedelta(days=1)
>>> print(tomorrow)
2019-12-23
>>> today < tomorrow
True
格式化输出
datetime
类中也提供了 strftime
和 strptime
方法,使用示例如下:
>>> import datetime
>>> format = "%a %b %d %H:%M:%S %Y"
>>> now = datetime.datetime.now()
>>> now
datetime.datetime(2019, 12, 22, 1, 7, 53, 505983)
>>> s = now.strftime(format)
>>> s
'Sun Dec 22 01:07:53 2019'
>>> datetime.datetime.strptime(s, format)
datetime.datetime(2019, 12, 22, 1, 7, 53)
三、calendar
这部分的功能目前还没用到,简单示例如下:
>>> import calendar
>>> c = calendar.TextCalendar(calendar.SUNDAY)
>>> c.prmonth(2019, 12)
December 2019
Su Mo Tu We Th Fr Sa
1 2 3 4 5 6 7
8 9 10 11 12 13 14
15 16 17 18 19 20 21
22 23 24 25 26 27 28
29 30 31
>>> cal = calendar.TextCalendar(calendar.SUNDAY)
>>> print(cal.formatyear(2020, 2, 1, 1, 3))
2020
January February March
Su Mo Tu We Th Fr Sa Su Mo Tu We Th Fr Sa Su Mo Tu We Th Fr Sa
1 2 3 4 1 1 2 3 4 5 6 7
5 6 7 8 9 10 11 2 3 4 5 6 7 8 8 9 10 11 12 13 14
12 13 14 15 16 17 18 9 10 11 12 13 14 15 15 16 17 18 19 20 21
19 20 21 22 23 24 25 16 17 18 19 20 21 22 22 23 24 25 26 27 28
26 27 28 29 30 31 23 24 25 26 27 28 29 29 30 31
April May June
Su Mo Tu We Th Fr Sa Su Mo Tu We Th Fr Sa Su Mo Tu We Th Fr Sa
1 2 3 4 1 2 1 2 3 4 5 6
5 6 7 8 9 10 11 3 4 5 6 7 8 9 7 8 9 10 11 12 13
12 13 14 15 16 17 18 10 11 12 13 14 15 16 14 15 16 17 18 19 20
19 20 21 22 23 24 25 17 18 19 20 21 22 23 21 22 23 24 25 26 27
26 27 28 29 30 24 25 26 27 28 29 30 28 29 30
31
...