Pyton-for-data-时间区间和区间处理
本文中主要介绍的是如何利用pandas进行时间区间处理
时间区间表示的是时间范围:天、月、季度、年等,Period类能够表示这种数据类型
import pandas as pd
import numpy as np
p = pd.Period(2007,freq='A-DEC')
p
Period('2007', 'A-DEC')
p + 5
Period('2012', 'A-DEC')
pd.Period(2017,freq='A-DEC') - p
<10 * YearEnds: month=12>
# 使用period_range
rng = pd.period_range('2020-01-01', '2020-06-30', freq='M')
rng
PeriodIndex(['2020-01', '2020-02', '2020-03', '2020-04', '2020-05', '2020-06'], dtype='period[M]', freq='M')
values = ['2020-01', '2020-02', '2020-03', '2020-04']
index = pd.PeriodIndex(values, freq='Q-DEC')
index
PeriodIndex(['2020Q1', '2020Q1', '2020Q1', '2020Q2'], dtype='period[Q-DEC]', freq='Q-DEC')
PeriodIndex类存储的是区间的序列,可以作为任意pandas数据结构的轴索引。
pd.Series(np.random.randn(6),index=rng)
2020-01 -0.254809
2020-02 0.384200
2020-03 0.440617
2020-04 -0.200929
2020-05 -0.290052
2020-06 1.803407
Freq: M, dtype: float64
# 使用字符串组
values = ['2001Q3','2002Q2','2003Q1']
index = pd.PeriodIndex(values
,freq='Q-DEC')
index
PeriodIndex(['2001Q3', '2002Q2', '2003Q1'], dtype='period[Q-DEC]', freq='Q-DEC')
使用的是asfreq:将区间和PeriodIndex对象转成其他的频率
A-DEC:给定月份所在月的最后一个工作日
p = pd.Period('2011',freq='A-DEC')
p
Period('2011', 'A-DEC')
# 使用asfreq方法
p.asfreq('M',how="start") # 从1月份开始
Period('2011-01', 'M')
# 使用asfreq方法
p.asfreq('M',how="end")
Period('2011-12', 'M')
p = pd.Period('2011',freq='A-JUN')
p
Period('2011', 'A-JUN')
p.asfreq('M',how="start") # 如果是start,表示从June往后退一年,也就是2010年7月份
Period('2010-07', 'M')
p.asfreq('M',how="end") # 如果是end,就是本身的月份
Period('2011-06', 'M')
# 高频率向低频率转换,pandas根据子区间的所属来决定父区间
p = pd.Period("Aug-2007","M")
p.asfreq("A-JUN")
Period('2008', 'A-JUN')
# 完整的PeriodIndex对象或者时间序列按照相同的语义进行转换
rng = pd.period_range("2015","2020",freq="A-DEC")
ts = pd.Series(np.random.randn(len(rng)),index=rng)
ts
2015 -0.429439
2016 0.378236
2017 0.476279
2018 0.198955
2019 0.107012
2020 0.192551
Freq: A-DEC, dtype: float64
ts.asfreq('M',how="start")
2015-01 -0.429439
2016-01 0.378236
2017-01 0.476279
2018-01 0.198955
2019-01 0.107012
2020-01 0.192551
Freq: M, dtype: float64
ts.asfreq("B",how="end")
2015-12-31 -0.429439
2016-12-30 0.378236
2017-12-29 0.476279
2018-12-31 0.198955
2019-12-31 0.107012
2020-12-31 0.192551
Freq: B, dtype: float64
季度区间是会计、金融和其他领域的标准。pandas支持从Q-JAN到Q-DEC的12个频率
p = pd.Period('2020Q4', freq="Q-JAN")
p
Period('2020Q4', 'Q-JAN')
p.asfreq("D","start")
Period('2019-11-01', 'D')
p.asfreq("D","end")
Period('2020-01-31', 'D')
rng = pd.period_range("2019Q3","2020Q4",freq="Q-JAN")
ts = pd.Series(np.arange(len(rng)),index=rng)
ts
2019Q3 0
2019Q4 1
2020Q1 2
2020Q2 3
2020Q3 4
2020Q4 5
Freq: Q-JAN, dtype: int64
new_rng = (rng.asfreq("B","e") - 1).asfreq("T","S") + 16 * 60
ts.index = new_rng.to_timestamp()
ts
2018-10-30 16:00:00 0
2019-01-30 16:00:00 1
2019-04-29 16:00:00 2
2019-07-30 16:00:00 3
2019-10-30 16:00:00 4
2020-01-30 16:00:00 5
dtype: int64
通过时间索引的Series和DataFrame可以被to_period方法转换成区间
rng = pd.date_range("2020-01-01",periods=6,freq="D") # 开始时间,指定长度和频率
ts = pd.Series(np.random.randn(6),index=rng)
ts # 年月日的格式,索引总存在相同的月份
2020-01-01 -0.715775
2020-01-02 -0.417415
2020-01-03 1.487385
2020-01-04 -0.570891
2020-01-05 -1.053310
2020-01-06 -1.895168
Freq: D, dtype: float64
pts = ts.to_period("M") # 转成年月格式,允许有相同的月份存在
pts
2020-01 -0.715775
2020-01 -0.417415
2020-01 1.487385
2020-01 -0.570891
2020-01 -1.053310
2020-01 -1.895168
Freq: M, dtype: float64
pts = ts.to_period()
pts
2020-01-01 -0.715775
2020-01-02 -0.417415
2020-01-03 1.487385
2020-01-04 -0.570891
2020-01-05 -1.053310
2020-01-06 -1.895168
Freq: D, dtype: float64
pts.to_timestamp(how="end")
2020-01-01 23:59:59.999999999 -0.715775
2020-01-02 23:59:59.999999999 -0.417415
2020-01-03 23:59:59.999999999 1.487385
2020-01-04 23:59:59.999999999 -0.570891
2020-01-05 23:59:59.999999999 -1.053310
2020-01-06 23:59:59.999999999 -1.895168
Freq: D, dtype: float64