datetime類是Python處理日期和時間的標準庫。datetime是date與time的結合體,包括date與time的所有信息。
它的構造函數如下:
datetime.datetime(year, month, day[, hour[, minute[, second[, microsecond[, tzinfo]]]]])
import time
from datetime import datetime, timedelta, timezone
1 datetime類定義的類屬性與方法
1.1 datetime.min、datetime.max
datetime所能表示的最小值與最大值。
print('datetime.max:' + str(datetime.max))
#datetime.max: 9999-12-31 23:59:59.999999
print('datetime.min:' + str(datetime.min))
#datetime.min: 0001-01-01 00:00:00
1.2 datetime.resolution
datetime最小單位。
print('datetime.resolution:' + str(datetime.resolution))
#datetime.resolution: 0:00:00.000001
1.3 datetime.today()
返回一個表示當前本地時間的datetime對象。
print('today():' + str(datetime.today()))
#today(): 2017-07-16 18:00:05.346294
1.4 datetime.now([tz])
返回一個表示當前本地時間的datetime對象,如果提供了參數tz,則獲取tz參數所指時區的本地時間。
print('now():' + str(datetime.now()))
#now(): 2017-07-16 18:00:05.346293
1.5 datetime.utcnow()
返回一個當前utc時間(世界標準時間)的datetime對象。(utc時間與北京時區相差8小時)
print('utcnow():' + str(datetime.utcnow()))
#utcnow(): 2017-07-16 10:00:05.346293
1.6 datetime.fromtimestamp(timestamp[,tz])
根據時間戮,創建一個datetime對象,參數tz指定時區信息。
print('fromtimestamp(tmstmp):' + str(datetime.fromtimestamp(time.time())))
#fromtimestamp(tmstmp): 2017-07-16 18:00:05.346294
1.7 datetime.utcfromtimestamp(timestamp)
根據時間戮,創建一個datetime對象。
print('utcfromtimestamp(tmstmp):' + str(datetime.utcfromtimestamp(time.time())))
#utcfromtimestamp(tmstmp):2017-07-16 10:00:05.346294
1.8 datetime.combine(date, time)
根據date和time,創建一個datetime對象。
d = date(2017,6,12)
t = time(18,04,25)
print('datetime.combine(date,time):' + str(datetime.combine(d,t)))
#datetime.combine(date,time): 2017-06-12 18:04:25
1.9 datetime.strptime(date_string, format)
將格式字符串轉換為datetime對象。
print(datetime.strptime("2017-07-16 18:06:19", "%Y-%m-%d %H:%M:%S"))
#2017-07-16 18:06:19
2 datetime類提供的實例方法與屬性
dt = datetime.strptime("2017-07-16 19:14:36", "%Y-%m-%d %H:%M:%S")
print(dt.year) # 2017
print(dt.month) # 7
print(dt.day) # 16
print(dt.hour) # 19
print(dt.minute) # 14
print(dt.second) # 36
print(dt.microsecond) # 0
print(dt.tzinfo) # None
print(dt.date()) # 2017-07-16
print(dt.time()) # 19:14:36
print(dt.replace(year=2018)) # 2018-07-16 19:14:36
print(dt.weekday()) # 6
print(dt.isocalendar()) # (2017, 28, 7)
print(dt.timetuple())
#返回日期對應的time.struct_time對象(類似于time模塊的time.localtime())
#time.struct_time(tm_year=2017, tm_mon=7, tm_mday=16, tm_hour=19, tm_min=14, tm_sec=36, tm_wday=6, tm_yday=197, tm_isdst=-1)
print(dt.utctimetuple())
#返回UTC日期對應的time.struct_time對象
#time.struct_time(tm_year=2017, tm_mon=7, tm_mday=16, tm_hour=19, tm_min=14, tm_sec=36, tm_wday=6, tm_yday=197, tm_isdst=0)
print(dt.toordinal())
#736526,返回日期對應的Gregorian Calendar日期
3 格式字符串datetime.strftime(format)
變量 | 說明 |
---|---|
%a | 星期的簡寫。如星期三為Web |
%A | 星期的全寫。如星期三為Wednesday |
%b | 月份的簡寫。如4月份為Apr |
%B | 月份的全寫。如4月份為April |
%c | 日期時間的字符串表示。(如:04/07/10 10:43:39) |
%d | 日在這個月中的天數(是這個月的第幾天) |
%f | 微秒(范圍[0,999999]) |
%H | 小時(24小時制,[0,23]) |
%I | 小時(12小時制,[0,11]) |
%j | 日在年中的天數 [001,366](是當年的第幾天) |
%m | 月份([01,12]) |
%M | 分鐘([00,59]) |
%p | AM或者PM |
%S | 秒(范圍為[00,61]) |
%U | 周在當年的周數當年的第幾周,星期天作為周的第一天 |
%w | 今天在這周的天數,范圍為[0,6],6表示星期天 |
%W | 周在當年的周數(是當年的第幾周),星期一作為周的第一天 |
%x | 日期字符串(如:04/07/10) |
%X | 時間字符串(如:10:43:39) |
%y | 2個數字表示的年份 |
%Y | 4個數字表示的年份 |
%z | 與utc時間的間隔(如果是本地時間,返回空字符串) |
%Z | 時區名稱(如果是本地時間,返回空字符串) |
%% | %% => % |
dt = datetime.now()
print('(%Y-%m-%d %H:%M:%S %f):'+ str(dt.strftime('%Y-%m-%d %H:%M:%S %f')))
#(%Y-%m-%d %H:%M:%S %f): 2017-07-16 20:32:19 033740
print('(%Y-%m-%d %H:%M:%S %p):'+str(dt.strftime('%y-%m-%d %I:%M:%S %p')))
#(%Y-%m-%d %H:%M:%S %p): 17-07-16 08:32:19 PM
print('%%a: %s' % dt.strftime('%a'))
#%a: Sun
print('%%A: %s' % dt.strftime('%A'))
#%A: Sunday
print('%%b: %s' % dt.strftime('%b'))
#%b: Jul
print('%%B: %s' % dt.strftime('%B'))
#%B: July
print('日期時間%%c: %s' % dt.strftime('%c'))
#日期時間%c: Sun Jul 16 20:32:19 2017
print('日期%%x:%s' % dt.strftime('%x'))
#日期%x:07/16/17
print('時間%%X:%s' % dt.strftime('%X'))
#時間%X:20:32:19
print('今天是這周的第%s天' % dt.strftime('%w'))
#今天是這周的第0天
print('今天是今年的第%s天' % dt.strftime('%j'))
#今天是今年的第197天
print('今周是今年的第%s周' % dt.strftime('%U'))
#今周是今年的第29周
4 日期和時間的常用操作
4.1 獲取當前、指定日期和時間
now = datetime.now() # 獲取當前datetime
print(now)
#2017-07-19 00:19:26.661741
print(type(now))
#<class 'datetime.datetime'>
datetime.now()返回當前日期和時間,其類型是datetime。
要指定某個日期和時間,我們直接用參數構造一個datetime:
dt = datetime(2017,7,19,8,30) # 用指定日期時間創建datetime
print(dt)
#2017-07-19 08:30:00
4.2 datetime和timestamp互相轉換
在計算機中,時間實際上是用數字表示的。我們把1970年1月1日 00:00:00 UTC+00:00時區的時刻稱為epoch time,記為0(1970年以前的時間timestamp為負數),當前時間就是相對于epoch time的秒數,稱為timestamp。
可認為:timestamp = 0 = 1970-1-1 00:00:00 UTC+0:00。對應的北京時間是:timestamp = 0 = 1970-1-1 08:00:00 UTC+8:00。
可見timestamp的值與時區毫無關系,因為timestamp一旦確定,其UTC時間就確定了,轉換到任意時區的時間也是完全確定的,這就是為什么計算機存儲的當前時間是以timestamp表示的,因為全球各地的計算機在任意時刻的timestamp都是完全相同的。
把一個datetime類型轉換為timestamp只需要簡單調用timestamp()方法:
dt = datetime(2017,7,19,8,30) # 用指定日期時間創建datetime
dt.timestamp() # 把datetime轉換為timestamp
#1500424200.0
將1500424200.0秒轉換為年份,得到47.57813926940639年,對應的就是1970+47=2017年。
要把timestamp轉換為datetime,使用datetime提供的fromtimestamp()方法:
t = 1500424200.0
print(datetime.fromtimestamp(t))
#2017-07-19 08:30:00
timestamp是一個浮點數,它沒有時區的概念,而datetime是有時區的。上述轉換是在timestamp和本地時間做轉換。本地時間是指當前操作系統設定的時區。
例如北京時區是東8區,則本地時間:2017-07-19 08:30:00,實際上就是UTC+8:00時區的時間:2017-07-19 08:30:00 UTC+8:00。而此刻的格林威治標準時間與北京時間差了8小時,也就是UTC+0:00時區的時間應該是:2017-07-19 00:30:00 UTC+0:00。
timestamp也可以直接被轉換到UTC標準時區的時間:
t = 1500424200.0
print(datetime.fromtimestamp(t)) # 本地時間
#2017-07-19 08:30:00
print(datetime.utcfromtimestamp(t)) # UTC時間
#2017-07-19 00:30:00
注意:某些編程語言(如Java和JavaScript)的timestamp使用整數表示毫秒數,這種情況下只需要把timestamp除以1000就得到Python的浮點表示方法。
4.3 str和datetime互相轉換
很多時候,用戶輸入的日期和時間是字符串,要處理日期和時間,首先必須把str轉換為datetime。轉換方法是通過datetime.strptime()實現,需要一個日期和時間的格式化字符串:
str2day = datetime.strptime('2017-7-19 12:20:30', '%Y-%m-%d %H:%M:%S')
print(str2day)
#2017-07-19 12:20:30
轉換后的datetime是沒有時區信息的,只是根據給定的字符串,進行轉換而已。
如果已經有了datetime對象,要把它格式化為字符串顯示給用戶,就需要轉換為str,轉換方法是通過strftime()實現的,同樣需要一個日期和時間的格式化字符串:
now = datetime.now()
print(now.strftime('%a, %b %d %H:%M'))
#Wed, Jul 19 00:49
4.4 datetime加減
對日期和時間進行加減實際上就是把datetime往后或往前計算,得到新的datetime。加減可以直接用+和-運算符,不過需要導入timedelta這個類:
now = datetime.now()
#now
datetime.datetime(2017, 7, 19, 0, 53, 2, 335063)
now + timedelta(hours=10)
#datetime.datetime(2017, 7, 19, 5, 53, 2, 335063)
now - timedelta(days=2)
#datetime.datetime(2017, 7, 17, 0, 53, 2, 335063)
now + timedelta(days=3, hours=10)
#datetime.datetime(2017, 7, 22, 10, 53, 2, 335063)
可見,使用timedelta你可以很容易地算出前幾天和后幾天的時刻。
4.5 本地時間轉換為UTC時間
本地時間是指系統設定時區的時間,例如北京時間是UTC+8:00時區的時間,而UTC時間指UTC+0:00時區的時間。
一個datetime類型有一個時區屬性tzinfo,但是默認為None,所以無法區分這個datetime到底是哪個時區,除非強行給datetime設置一個時區:
tz_utc_8 = timezone(timedelta(hours=8)) # 創建時區UTC+8:00
now = datetime.now()
now
#datetime.datetime(2017, 7, 19, 1, 17, 59, 785108)
dt = now.replace(tzinfo=tz_utc_8) # 強制設置為UTC+8:00
dt
#datetime.datetime(2017, 7, 19, 1, 17, 59, 785108, tzinfo=datetime.timezone(datetime.timedelta(0, 28800)))
如果系統時區恰好是UTC+8:00,那么上述代碼就是正確的,否則,不能強制設置為UTC+8:00時區。
4.6 時區轉換
先通過utcnow()拿到當前的UTC時間,再轉換為任意時區的時間:
- 拿到UTC時間,并強制設置時區為UTC+0:00:
utc_dt = datetime.utcnow().replace(tzinfo=timezone.utc)
print(utc_dt)
#2017-07-18 17:21:31.636243+00:00
- astimezone()將轉換時區為北京時間:
bj_dt = utc_dt.astimezone(timezone(timedelta(hours=8)))
print(bj_dt)
#2017-07-19 01:21:31.636243+08:00
- astimezone()將轉換時區為東京時間:
tokyo_dt = utc_dt.astimezone(timezone(timedelta(hours=9)))
print(tokyo_dt)
#2017-07-19 02:21:31.636243+09:00
- astimezone()將bj_dt轉換時區為東京時間:
tokyo_dt2 = bj_dt.astimezone(timezone(timedelta(hours=9)))
print(tokyo_dt2)
#2017-07-19 02:21:31.636243+09:00
時區轉換的關鍵在于,拿到一個datetime時,要獲知其正確的時區,然后強制設置時區,作為基準時間。利用帶時區的datetime,通過astimezone()方法,可以轉換到任意時區。
注意:不是必須從UTC+0:00時區轉換到其他時區,任何帶時區的datetime都可以正確轉換,例如上述bj_dt到tokyo_dt的轉換。
如果您發現文中有不清楚或者有問題的地方,請在下方評論區留言,我會根據您的評論,更新文中相關內容,謝謝!