Python 的 DataFrame 摘要

作者: , 共 4190 字

Python 数据分析工具 pandas 中以 DataFrame 和 Series 作为主要的数据结构。

Series 是一个数据序列。DataFrame 是一张数据表(可以理解由多个 Series 构成,每个 Series 为一列)。DataFrame 和 Excel 和数据库的数据表类似(实际结构更复杂,因为支持多重索引),因此可以对其做类似 Excel 数据表的排序、筛选、聚合、透视表等操作,也可以做类似于数据库数据表的多表关联( join )等操作。

1. 建立 DataFrame 对象

df = pd.DataFrame() #创建DataFrame对象 
df = pad.DataFrame([[1,2],[3,4]], columns=list('AB'))

1.1. 从文件读入

df = pandas.read_json('abc.json')
df = pandas.read_csv('abc.csv', sep=';', nrows=2) # 首先输入csv文本地址,然后分割符选择等等

1.2. 保存到文件

df.to_csv('abc.csv', encoding="utf8") # 要支持中文,python2必须指定encoding。python3已默认使用utf8
df.to_excel('foo.xlsx',sheet_name='Sheet1');pd.read_excel('foo.xlsx', 'Sheet1', index_col=None, na_values=['NA'])#写入读取excel数据,pd.read_excel读取的数据是以DataFrame形式存储
df.to_hdf('foo.h5','df');pd.read_hdf('foo.h5','df')#写入读取HDF5数据

2. 查看 DataFrame 数据及属性

df.dtypes #查看各行的数据格式
df['col1'].astype(int)#转换某列的数据类型
df.head() #查看前几行的数据,默认前5行
df.tail() #查看后几行的数据,默认后5行
df.index #查看索引
df.columns #查看列名
df.values #查看数据值
df.describe() #描述性统计
df.T #转置

3. 选择数据

df[1:-3] # 获取1到倒数第三行
df.ix[1:3] # 同上 
df.ix[1:3[1,3]]#获取1列3列的1~3行数据
df['c1'] # 选择列
df.c1 # 效果同上
df.columns[[0,1,3]] # zero indexed

需要注意 DataFrame 取下标和索引速度非常慢,不建议对其做 for 循环操作,若要做循环操作,建议两种替换方案,一种使用内建函数( apply、map、trasnform )等,另外一种将每列 Series 转为 list 之后处理( col_list = df.col.tolist())。

4. 筛选数据(保留对应的行)

alist = ['023-18996609823']
df['code'].isin(alist) #将要过滤的数据放入字典中,使用isin对数据进行筛选,返回行索引以及每行筛选的结果,若匹配则返回ture
df[df['code'].isin(alist)] #获取匹配结果为ture的行
df[df.value>0]
df[df['plan'].str.contains(r'.*?语音CDMA.*')] #使用正则表达式进行模糊匹配,*匹配0或无限次,?匹配0或1次

5. 删除数据

df[columns].drop_duplicates() #剔除重复行数据
df[df.isnull()]
df[df.notnull()]
df.dropna()#将所有含有nan项的row删除
df.dropna(axis=1,thresh=3) #将在列的方向上三个为NaN的项删除
df.dropna(how='ALL')#将全部项都是nan的row删除填充值

5.1. 删除特定列

del df.col1  # 删除列 inplace
df = df.drop('column_name', 1) # 返回删除后的新的DataFrame
df.drop('column_name', axis=1, inplace=True)
df.drop([df.columns[[0, 1, 3]]], axis=1, inplace=True)   # Note: zero indexed

6. 修改数据

6.1. 修改列名

df.rename(columns={'A':'a', 'C':'c'}, inplace=True)
df.columns = ['A', 'B', 'C']

df.c
df.fillna(0)
df.fillna({1:0,2:0.5}) #对第一列nan值赋0,第二列赋值0.5
df.fillna(method='ffill') #df
df.ix[1:3,[1,3]]=1#所选位置数据替换为1   
df['支局_维护线'] = df['支局_维护线'].str.replace('巫溪分公司(.{2,})支局','\1')#可以使用正则表达式

6.2. 新增列

df['new_column'] = df['old_column']   # 新增了一列 
df.new_column = df['old_column']      # 这样不会新增列,只会跟原列起了个别名引用

7. apply

df.apply(lambda col: sum(col), axes=0) # 对每列求和
df.apply(lambda row: sum(row), axes=0) # 对每行求和
df.col2 = df.col1.apply(lambda col: sum(col))    # 对col1列求和
df.col3 = df.col3.apply(lambda x: x+1) # col3列都加1
df = df.applymap(lambda x:x+1) # 每个元素都加1
df.transform(lambda x:x+1)     # 效果同上,相当于inplace的applymap

8. 聚合数据(类似 SQL 中的 GROUP BY 或 HAVING):

df.groupby(['col1', 'col2']) # 将数据
 data_obj.groupby('支局_维护线')['用户标识'] #上面的简单写法
 adsl_obj.groupby('支局_维护线')['用户标识'].agg([('ADSL','count')])#按支局进行汇总对用户标识进行计数,并将计数列的列名命名为ADSL

9. 透视表

df = df.pivot(index='A', columes='B', values='C') # 先聚合再透视。
table = pivot_table(df, values='D', index=['A', 'B'], columns=['C'], aggfunc=np.sum) # 复杂一点的,支持同时聚合

10. 合并数据集(类似于数据库的 union/union all )

df1 = df1.append(df2) # df2放在df1后面,注意append会返回一个新的对象,不是在原对象上修改。
df = pandas.concat([df1, df2], ignore_index=True) # 等价于append

11. Join 数据集(类似于数据库的 left/right/inner/outer join )

df = pandas.concat([df1, df2], axis=1) # 和sql的join类似,on index_key
merge(df1, df2, on='abc',how='inner')# df1和df2将用户标识当成重叠列的键合并两个数据集,inner表示取两个数据集的交集.
pd.merge(left, right, how='inner', on=None, left_on=None, right_on=None,
         left_index=False, right_index=False, sort=True,
         suffixes=('_x', '_y'), copy=True, indicator=False)

12. 排序

df.sort_values(by, axis=0, ascending=True, inplace=False, kind='quicksort', na_position='last')

13. 画图

Q. E. D.

类似文章:
Excel 多表合并和查询是一个应用很广泛的问题。下面是一个简单的例子,我们需要从两张数据表里,得出每个行业的股票波动率平均值。第一个数据表保存了股票和行业的对应关系,有两列,第一列为股票名,第二列为每只股票对应的行业。第二张表保存了各个股票在各个交易日的收盘价和前收盘价,有四列,第一列是股票名,第二列为交易日,第三列和第四列分别为股票在这个交易日的前收盘价和收盘价。
编程 » Excel, 数据库
在前面的文章里,我已经提到Excel 数据本身可以当做一张 SQL 查询的数据表,并在 Excel 内进行数据库运算操作。数据库查询函数可以用我之前写的Excel 数据库操作函数类。我们可以用以下方式
编程 » SQL
现在 Access 用的人应该不多了,本来我以为我也不可能用这玩意儿,但最近在用 VBA 通过 SQL 处理数据时,发现它的语法是 Access 的语法。平时对 SQL Server 语法相对熟悉一些。下文总结了 Access 和 SQL Server 语法的差异。
更新一下之前写的Excel 的数据库类,将其改成函数的形式,调用更简单(省却了生成类实例的步骤)。现在这个代码在工作中用了一年多,已经比较健壮。若有问题,请留言指出或与我联系。
2014-03-25 更新:我已经将该类修改成函数形式,并增加新功能,参见更新 Excel 的数据库查询函数库
编程 » C++, C++11
花括号初始化是C++11引入的一种初始化方法。
Excel 有一个很有用的功能是直接导入外部数据库或者使用外部数据源建立数据透视表和数据透视图。但比较可惜的是,这个数据源的查询语句是静态的,它无法根据日期自动修改(比如在应用中,我们希望每天获取的外部数据都是当天最新的数据),下面两个函数是修改外部数据源的 VBA 代码,调用它们就可以建立动态的数据源。
最近分级 A 的价格不断被打压,再加上股市处于下降通道,看跌期权价值不断提升,导致分级 A 出现一个历史上绝无仅有的买入机会。
假设我手里有一些股票,成分和指数差不多,想用股指期货去对冲,应该卖空多少数量的股指期货?