时间序列
文章目录
pandas时间序列
- time series
- 结构化数据形式
- 时间戳,timestamp,特定的时刻
- 固定时期,period
- 时间间隔,interval
时间序列基础
DatetimeIndex
-
pandas中的datetime对象
-
ts = pd.Series(np.random.randn(6), index=pd.date_range('2018/11/11',period=6)) ts.index # DatetimeIndex,时间戳 ts.index.dtype # 用Numpy的datetime64数据类型以 纳秒 形式存储时间戳 ts.index[0] # Timestamp
对Series的操作
-
索引
ts['2018/11/11'] ts['20181111'] ts['2018'] ts['2018/11']
-
切片
ts[datetime(2018,11,11):] ts['2018/11/11':'2019/11/11'] # 用不存在与该时间序列中的时间戳切片
-
过滤
ts.truncate(after='2018/11/12')
对DataFrame的操作
-
对DataFrame的操作
df.loc['2018/11']
-
对非唯一时间戳聚合
df.index.is_unique # 属性判断索引是否唯一 df.groupby(level=0).mean()
重采样
-
resampling
- 将时间序列从一个频率转换到另一个频率的处理过程
- 高频率 聚合 低频率——降采样(downsampling)
- 升采样(upsampling):低频率数据 转换到 高频率
- 并不是所有的重采样,都被划分为这两大类
- W-WED(每周三)转换为W-FRI,既不是降采样也不是升采样
ts.resample('D') #字符串‘D’是每天的意思 ts.resample('M',kind='period').mean()
- 将时间序列从一个频率转换到另一个频率的处理过程
resample方法的参数
-
ts.resample(freq=, # 重采样频率的字符串 axis=, # 重采样的轴,默认axis=0 fill_method=, # 升采样如何插值:‘ffill’,‘bfill’ closed=, # 降采样中,各时间段的哪一端是闭合的,right(默认)或left label=, # 降采样中,如何设置聚合值的标签,right或left loffset=, # 面元标签的时间校正值 limit=, # 在前向或后向填充时,允许填充的最大时期数 kind= # 聚合到时期或时间戳,默认居合值时间序列的索引类型 )
截取
Series.dt.year.values_counts()
pd.to_datetime(df['col']).dt.month
生成日期范围
-
pd.date_range
pd.date_range('2019/02/02',period=10) pd.date_range(end = '2019/02/02',period=10) pd.date_range('2018/11/11','2019/11/11',freq='BM')
-
时间序列频率
别名 偏移量类型 说明 D Day 每日历日 B BusinessDay 每工作日 H Hour 每小时 T或min Minute 每分 S Second 每秒 L或ms Milli 每毫秒 U Micro 每微妙 M MonthEnd 每月最后一个日历日 BM BusinessMonthEnd 每月最后一个工作日 MS MonthBegin 每月第一个日历日 BMS BusinessMonthBegin 每月第一个工作日 W-MON
W-TUEWeek 从指定的星期几(MON、TUE、WED、THU、FRI、SAT、SUN)开始算起 WOM-1MON
WOM-2MONWeekOfMonth 产生每月第一、第二、第三或第四周的星期几
WOM-3FRI:每月第3个星期五Q-JAN
Q-FEBQuarterEnd 对于以指定月份(JAN、FEB、MAR、APR、MAY、JUN、JUL、AUG、SEP、OCT、NOV、DEC)结束的年度,每季度最后一月的最后一个日历日 BQ-JAN
BQ-FEBBusinessQuarterEnd 对于以指定月份结束的年度,每季度最后一月的最后一个工作日 QS_JAN
QS_FEBQuarterBegin 对于以指定月份结束的年度,每季度最后一月的第一个日历日 BQS_JAN
BQS-FEBBusinessQuarterBegin 对于以指定月份结束的年度,每季度最后一月的第一个工作日 A_JAN
A-FEBYuerEnd 每年指定月份(JAN、FEB、MAR、APR、MAY、JUN、JUL、AUG、SEP、OCT、NOV、DEC)的最后一个日历日 BA_JAN
BA-FEBBusinessYearEnd 每年指定月份的最后一个工作日 AS-JAN
AS-FEBYearBegin 每年指定月份的第一个日历日 BAS-JAN
BAS-FEBBusinessYearBegin 每年指定月份的第一个工作日 -
normalize选项
- 产生一组被规范化(normalize)到午夜的时间戳
pd.date_range('2018/11/11 12:11:23',period=6,normalize=True)
日期偏移量
-
date offset
-
hour = pd.tseries.offsets.Hour() four_hours = pd.tseries.offsets.Hour(4) # 日期偏移量对日期进行位移 now = datetime.datetime(2018,11,11) now + 3 * pd.tseries.offsets.Day() now + pd.tseries.offsets.MonthEnd() # 锚点偏移量(MonthEnd)
移动(超前或滞后)数据
-
移动shifting
- 沿着时间轴将数据前移或后移
- Series和DataFrame都有一个shift方法用于执行单纯的前移或后移操作
- 保持索引不变
ts = pd.Series(np.random.randn(4), index=pd.date_range('2018/11/11', periods=4, freq='M')) ts.shift(2) ts.shift(-2)
-
如果频率已知,则可以将传给shift以便实现对时间戳进行位移而不是对数据进行简单位移
ts.shift(2,freq='M')
datetime模块
-
datetime模块的数据类型
- datetime.datetime,日期和时间
- datetime.time,时、分、秒、毫秒
- datetime.date,公历年、月、日
- datetime.timedelta,两个datetime.datetime值之差(日,秒,毫秒)
-
datetime.datetime
- 毫秒形式存储日期和时间
from datetime import datetime now = datetime.now() now.day now.year, now.month
-
datetime.timedelta
- 两个datetime.datetime对象之间的时间差
delta = datetime(2018,11,11) - datetime(2019,11,11) delta.days delta.seconds datetime(2018,11,11) + 2 * datetime.timedelta(12)
转换
字符串 与 datetime.datetime相互转换
datetime.datetime–>str
-
datetime.datetime–>str
stamp = datetime.datetime(2018,11,22) str(stamp) stamp.strftime('%Y/%m-%d')
str --> datetime.datetime
-
- datetime.strptime
- 需要已知日期格式
value = '2018-11-22' datetime.strptime(value,'%Y-%m-%d') datestrs = ['7/18/2018','8/17/2018'] [datetime.strptime(x,'%m/%d/%Y') for x in datestrs]
-
parse()
-
–>datetime.datetime
-
解析几乎所有人类能够理解的日期形式
-
不需知道日期格式
-
from dateutil.parse import parse parse('2018/12/22') parse(value) parse('Jan 31,1997 10:45 PM') # 参数 parse('6/12/2018',dayfirst=True) # 日出现在月的前面
- pd.to_datetime()
pd.to_datetime(datestrs)
- datetime.strptime
datetime格式
代码 | 说明 |
---|---|
%Y | 4位年 |
%y | 2位年 |
%m | 2位月[01,12] |
%d | 2位日[01,31] |
%H | 时[00,23] |
%I | 时[01,12] |
%M | 2位分[0,29] |
%S | 秒[00,61],(60和61用于闰秒) |
%w | 整数表示星期几[0(星期天),6] |
%U | 每年的第几周[00,53] 星期天是每周的第一天 每年第一个星期天之前的几天:第0周 |
%W | 每年的第几周[00,53] 星期一是每周的第一天 每年第一个星期一之前的几天:第0周 |
%z | 以+HHMM或-HHMM表示的UTC时区偏移量 如果时区为naive,则返回空字符串 |
%F | %Y-%m-%d的简写 |
%D | %m/%d/%y的简写 |
pd.to_datetime
df.col = pd.to_datetime(df.col,format="%Y/%m/%d")
- format
- Y:四位年份,2018
- y:2位年份,18
- m:月份
- M:分钟
- d:day
.astype()转换时间维度
- 年月日,转换到月份、年份
df.col.values.astype("datetime64[M]")# 读取到月
df.col.values.astype("datetime64[Y]")# 读取到年
去除单位
df.col / np.timedelta64(1,'D')
转换时间维度
-
同时使用与文字分组,不更改col1的数据类型
df.col1[1]为'23/01/2018' df.set_index('col1',inplace=True) df.groupby(lambda col1:col1.split('/')[2])
- 将col1列设置为index
- 对index分组,匿名函数中split后取‘年’为分割点
- 注意,不把col1列更改为DatetimeIndex(时间戳)
聚类分组时间序列
用0替换分和秒
-
dt = datetime.datetime(2011, 10, 29, 20, 30, 21) In [110]: dt.replace(minute=0, second=0) Out[110]: datetime.datetime(2011, 10, 29, 20, 0)
DatetimeIndex
转换为时间序列index
-
设置index格式为DatetimeIndex,并引用date列的值
df.index=pd.DatetimeIndex(df['col'])
-
根据字符串样式,解析日期
df.['col']=pd.to_datetime(df['col'],format='%Y-%m/%d')
By 儒冠多误身 2019/04/21