6-Pandas時間序列處理之時區處理(UTC查看、獲取、時區意識型TimeStamp對象、本地化與轉換、計算)


  通常選擇使用協調世界時UTC,又稱世界統一時間、世界標准時間、國際協調時間)來處理時間序列。

  時區以UTC偏移量的形式表示的。

  在Python中,時區信息來自第三方庫pytz,Pandas包裝了pytz功能。時區名可以在文檔中找到,也可以用交互的方式查看。

  關於pytz模塊的信息,可參考【python模塊——pytz】

 

(1)查看時區

  pytz有all_timezones、common_timezones這兩個屬性來查看有哪些時區

>>> import pytz
>>> len(pytz.common_timezones)
440
>>> pytz.common_timezones[:5]
['Africa/Abidjan', 'Africa/Accra', 'Africa/Addis_Ababa', 'Africa/Algiers', 'Africa/Asmara']
>>> pytz.common_timezones[-5:]
['US/Eastern', 'US/Hawaii', 'US/Mountain', 'US/Pacific', 'UTC']

>>> len(pytz.all_timezones)
592
>>> pytz.all_timezones[:5]
['Africa/Abidjan', 'Africa/Accra', 'Africa/Addis_Ababa', 'Africa/Algiers', 'Africa/Asmara']
>>> pytz.all_timezones[-5:]
['UTC', 'Universal', 'W-SU', 'WET', 'Zulu']

 (2)獲取時區對象

  pytz有timezone屬性獲取時區對象

>>> tz = pytz.timezone('Asia/Shanghai')
>>> tz
<DstTzInfo 'Asia/Shanghai' LMT+8:06:00 STD>

 (3)查看時間序列的時區

  Pandas中的時間序列默認是naive時區,即沒有時區。用index.tz方法查看時間序列的時區

>>> rng = pd.date_range('2020/8/1',periods=5,freq='D')
>>> ts
2020-08-01    4
2020-08-02    8
2020-08-03    3
2020-08-04    3
2020-08-05    7
Freq: D, dtype: int32
>>> print(ts.index.tz)
None

  通過參數tz可以設置時區

>>> rng2 = pd.date_range('2020/8/1',periods=5,freq='D',tz='UTC')
>>> ts2 = pd.Series(np.random.randint(1,10,len(rng2)),index = rng2)
>>> ts2
2020-08-01 00:00:00+00:00    8
2020-08-02 00:00:00+00:00    3
2020-08-03 00:00:00+00:00    1
2020-08-04 00:00:00+00:00    3
2020-08-05 00:00:00+00:00    2
Freq: D, dtype: int32
>>> print(ts2.index.tz)
UTC

  (4)本地化和轉換

  時間序列若需要和轉化,必須先使用tz_localize進行時區本地化,再通過tz_convert()轉換成別的時區

#先進行本地化轉換到別的地區
>>> ts_utc = ts.tz_localize('UTC')
>>> ts_utc.index
DatetimeIndex(['2020-08-01 00:00:00+00:00', '2020-08-02 00:00:00+00:00',
               '2020-08-03 00:00:00+00:00', '2020-08-04 00:00:00+00:00',
               '2020-08-05 00:00:00+00:00'],
              dtype='datetime64[ns, UTC]', freq='D')

#再轉換到別的時區
>>> ts_utc.tz_convert('US/Eastern')
2020-07-31 20:00:00-04:00    4
2020-08-01 20:00:00-04:00    8
2020-08-02 20:00:00-04:00    3
2020-08-03 20:00:00-04:00    3
2020-08-04 20:00:00-04:00    7
Freq: D, dtype: int32

  DatetimeIndex日期索引對象也可以使用tz_localize()和tz_convert()方法

>>> ts.index = ts.index.tz_localize('Asia/Shanghai')
>>> ts
2020-08-01 00:00:00+08:00    4
2020-08-02 00:00:00+08:00    8
2020-08-03 00:00:00+08:00    3
2020-08-04 00:00:00+08:00    3
2020-08-05 00:00:00+08:00    7
Freq: D, dtype: int32

  (5)操作時區意識型TimeStamp對象

  與時間序列和日期范圍一樣,時間戳對象也能從naive本地化為時區意識型(time zone-aware),並從一個時區轉換到另一個時區

 :創建一個時間戳本地化到世界標准時間UTC,並將時區轉換為'US/Eastern'

>>> stamp = pd.Timestamp('2020-8-1 18:23:34')
>>> stamp_utc = stamp.tz_localize('UTC')
>>> stamp_utc
Timestamp('2020-08-01 18:23:34+0000', tz='UTC')
>>> stamp_utc_convert = stamp_utc.tz_convert('US/Eastern')
>>> stamp_utc_convert
Timestamp('2020-08-01 14:23:34-0400', tz='US/Eastern')

  注意:時區意識型對象在內部保存了一個UTC時間戳,其值在時區轉換過程中是不是發生改變的,是從1970年1月1日算起的納秒數

如:stamp_utc和stamp_utc_convert的值是一樣的

>>> stamp_utc_convert.value
1596306214000000000
>>> stamp_utc.value
1596306214000000000

  (6)不同時區之間的計算

  當兩個時間序列的時期不同,若需要將其合並,最后的結果將會是UTC

>>> rng = pd.date_range('2020/8/1',periods=5,freq='D')
>>> rng = pd.date_range('2020/8/1 10:30',periods=5,freq='D')
>>> ts = pd.Series(np.random.randint(1,10,len(rng)),index = rng)
>>> ts
2020-08-01 10:30:00    8
2020-08-02 10:30:00    1
2020-08-03 10:30:00    9
2020-08-04 10:30:00    9
2020-08-05 10:30:00    3
Freq: D, dtype: int32

>>> ts1 = ts[:2].tz_localize('Europe/Zurich')
>>> ts2 = ts[2:4].tz_localize('US/Arizona')
>>> ts1.index
DatetimeIndex(['2020-08-01 10:30:00+02:00', '2020-08-02 10:30:00+02:00'], dtype='datetime64[ns, Europe/Zurich]', freq='D')
>>> result = ts1 + ts2
>>> result
2020-08-01 08:30:00+00:00   NaN
2020-08-02 08:30:00+00:00   NaN
2020-08-03 17:30:00+00:00   NaN
2020-08-04 17:30:00+00:00   NaN
dtype: float64
>>> result.index
DatetimeIndex(['2020-08-01 08:30:00+00:00', '2020-08-02 08:30:00+00:00',
               '2020-08-03 17:30:00+00:00', '2020-08-04 17:30:00+00:00'],
              dtype='datetime64[ns, UTC]', freq=None)

 

  


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM