Python3 - 时间处理模块

1 简介

datetime模块包含了很多类,比如datetime, date, time, timedelta, timezone等等。这里只讲解datetime与timedelta,以及timezone。

2 datetime类

datetime类包含了date与time。

2.1 返回本地或其他时区的当前时间

classmethod datetime.now(tz=None)返回一个datetime对象,tz参数默认情况下表示本地的当前时间,若指定一个其他时区对应的timezone对象,则表示该时区的当前时间。 classmethod datetime.utcnow()返回一个datetime对象,表示当前的UTC时间,也即UTC+0:00时区的当前时间。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
from datetime import datetime, timedelta, timezone

# 获取本地时区的当前时间。
# 2015-08-26 14:53:29.333231
print(datetime.now())

# 设置时区为utc+6:00,并返回相应的timezone对象。
tz_utc_6 = timezone(timedelta(hours = 6))
# 返回UTC+6:00的当前时间。
# 2015-08-26 12:53:29.333276+06:00
print(datetime.now(tz_utc_8))

# 获取当前的UTC时间,也即UTC+0:00时区的当前时间。
# 2015-08-26 06:53:29.333413
print(datetime.utcnow())

2.2 生成一个指定日期时间的datetime对象

构造函数datetime(year, month, day, hour=0, minute=0, second=0, microsecond=0, tzinfo=None)。

1
2
3
4
5
6
7
8
from datetime import datetime, timedelta, timezone

# 生成一个UTC+6:00时区的timezone对象。
tz_utc_6 = timezone(timedelta(hours = 6))
# microsecond参数采用默认值。
dt = datetime(2015, 4, 19, 12, 20, tzinfo = tz_utc_6)
# 2015-04-19 12:20:00+06:00
print(dt)

2.3 通过改变datetime对象的属性生成一个新的datetime对象

datetime实例方法replace([year[, month[, day[, hour[, minute[, second[, microsecond[, tzinfo]]]]]]]])。

1
2
3
4
5
6
7
8
9
10
11
from datetime import datetime, timedelta, timezone

# 先生成一个datetime对象。
tz_utc_6 = timezone(timedelta(hours = 6))
dt = datetime(2015, 4, 19, 12, 20, 3, 4, tzinfo = tz_utc_6)
# 2015-04-19 12:20:03.000004+06:00
print(dt)

# 然后改变这个datetime对象的tzinfo参数对应的时区属性为UTC+0:00时区后,新生成一个datetime对象。
# 2015-04-19 12:20:03.000004+00:00
print(dt.replace(tzinfo = timezone.utc))

2.4 表示时间的str类型的字符串与datetime类型的对象当相互转换

classmethod datetime.strptime(date_string, format)。将一个表示时间的str类型的字符串按照格式读取后,转变为datetime类型的对象。第一个参数为表示时间的字符串,第二个参数是格式字符串。 datetime.strftime(format)。将一个datetime类型的对象按照格式转变为一个str类型的字符串。

1
2
3
4
5
6
7
8
9
10
11
from datetime import datetime

# 注意第一个参数对应字符串的格式一定要与第二个参数对应字符串的格式匹配。其中%z需要与+HHMM或者-HHMM匹配。
dt = datetime.strptime("2015-6-1 18:19:59+0600", "%Y-%m-%d %H:%M:%S%z")
# 2015-06-01 18:19:59+06:00
print(dt)

# 首先生成一个datetime对象,然后将其按照格式转变为str类型的字符串。
tz_utc_6 = timezone(timedelta(hours = 6))
dt = datetime(2015, 4, 19, 12, 20, tzinfo = tz_utc_6)
print(dt.strftime("%Y-%m-%d %H:%M:%S%z"))

2.5 timestamp时间与datetime对象之间的转换

在计算机中,时间实际上是用数字表示的。我们把1970年1月1日 00:00:00 UTC+00:00时区的时刻称为epoch time,记为0(1970年以前的时间timestamp为负数),当前时间就是相对于epoch time的秒数,称为timestamp。timestamp的值与时区毫无关系,因为timestamp一旦确定,则可以转换到任意时区的时间。这就是为什么计算机存储的当前时间是以timestamp表示的,因为全球各地的计算机在任意时刻的timestamp都是完全相同的。 Python的timestamp是一个浮点数,小数位表示毫秒数。

datetime.timestamp()。将一个datetime对象转换成timestamp时间。 classmethod datetime.fromtimestamp(timestamp, tz=None)。将一个timestamp时间转换成本地时区或者其他时区的datetime对象。

1
2
3
4
5
6
7
8
9
10
from datetime import datetime, timedelta, timezone

# 首先生成一个datetime对象,然后转换成timestamp时间。
tz_utc_6 = timezone(timedelta(hours = 6))
dt = datetime(2015, 4, 19, 12, 20, 3, 4, tzinfo = tz_utc_6)
print(dt.timestamp())

# 将一个浮点数表示的timestamp时间转换成本地时区的datetime对象。
ts = 123456789.0
print(datetime.fromtimestamp(ts))

2.6 时区转换

上面通过replace()方法修改时区时,只是简单地将时区更改了,时间仍为发生变化,这在正常的时区转换情况中,是不合理的。假如要想在改变时区时,相应地调整时间和日期,就要用到一下方法。 datetime实例方法astimezone(tz=None)。返回一个新的datetime对象。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
from datetime import datetime, timedelta, timezone

# 先生成一个datetime对象。
tz_utc_6 = timezone(timedelta(hours = 6))
dt = datetime(2015, 4, 19, 12, 20, 3, 4, tzinfo = tz_utc_6)
# 2015-04-19 12:20:03.000004+06:00
print(dt)

# 运用replace()方法替换时区。
# 2015-04-19 12:20:03.000004+08:00
print(dt.replace(tzinfo = timezone(timedelta(hours = 8))))

# 运用astimezone()方法替换时区。
# 2015-04-19 14:20:03.000004+08:00
print(dt.astimezone(timezone(timedelta(hours = 8))))

2.7 date 对象和 time 对象

datetime 对象有两个方法,date() 方法可以得到一个 date 对象,time() 方法可以得到一个 time 对象。

date 对象可以分别获取 year, month, day 这三个属性;time 对象可以分别获取 hour, minute, second, microsecond 这几个属性。

1
2
3
4
5
6
7
8
9
from datetime import datetime

d = datetime.now()

# 2016。
print(d.date().year)

# 22。
pirnt(d.time().hour)

3 timedelta类

timedelta对象表示一段时间,通常用于datetime对象表示的日期和时间的增减,以及timezone对象表示的时区的增减。

3.1 生成一个指定属性的timedelta对象

构造函数timedelta(days=0, seconds=0, microseconds=0, milliseconds=0, minutes=0, hours=0, weeks=0)。返回一个timedelta对象,只会保存天数(days),秒数(seconds),微秒(microseconds)这三个单位的值。

1
2
3
4
5
6
7
8
9
10
11
12
from datetime import timedelta

temp = timedelta(days = 1000, seconds = 8723, minutes = 23, microseconds = 9 0232, hours = 24, weeks = 90)
# 1631 days, 2:48:23.090232
print(temp)

# 1631
print(temp.days)
# 10103
print(temp.seconds)
# 90232
print(temp.microseconds)

3.2 datetime对象加上或减去一个timedelta对象

1
2
3
4
5
6
7
8
9
10
from datetime import datetime, timedelta, timezone

dt = datetime(2015, 5, 18, 16, 57, 3, 540997, timezone(timedelta(hours = 6)))
# 2015-05-18 16:57:03.540997+06:00
print(dt)

# 2015-05-19 02:57:03.540997+06:00
print(dt + timedelta(hours = 10))
# 2015-05-17 16:57:03.540997+06:00
print(dt - timedelta(days = 1))

3.3 两个datetime对象相减得到的差值为一个timedelta对象

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
from datetime import datetime, timedelta, timezone

dt = datetime(2015, 5, 18, 16, 57, 3, 840234, timezone(timedelta(hours = 6)))
# 2015-05-18 16:57:03.840234+06:00
print(dt)

dt2 = datetime(1000, 3, 17, 10, 23, 1, 540997, timezone(timedelta(hours = 6)))
# 1000-03-17 10:23:01.540997+06:00
print(dt2)

temp = dt - dt2
# <class 'datetime.timedelta'>
print(type(temp))
# 370783 days, 6:34:02.299237
print(temp)

4 timezone类

timezone对象表示时区。

构造函数timezone(offset[, name])。offset参数是一个与UTC时间(UTC+0:00)的差值对应的timedelta对象。

1
2
3
4
5
6
7
8
9
10
from datetime import timedelta, timezone

# UTC+06:00
print(timezone(timedelta(hours = 6)))

# UTC-05:00
print(timezone(-timedelta(hours = 5)))

#UTC+00:00
print(timezone.utc)


Reference