最常用的金融科技语言——Python

在建模的时间与精力分配中,数据的理解、整理与准备占据了整个工作的80%工作量。因此,提高数据准备工作的效率可以将更重要的时间分配到模型研究上,从而提升数据建模的效率与正确率。

数据的整理与准备,一般涉及以下8点:

  1. 缺失值识别与处理
  2. 异常值识别与处理
  3. 重复值识别与处理
  4. 数值替换
  5. 行列名变更
  6. 离散数据分箱
  7. 随机取样
  8. 类别变量转换哑变量(Dummy Variables)

接下来文章将逐一总结以上各点的意义及常见操作手段。

以下操作均使用pandas及numpy包

默认

import pandas as pdimport numpy as np

#1缺失值

数据缺失在数据建模中非常常见,几乎每一次数据分析都会遇到。缺失值的处理一般涉及2个步骤:识别、处理。在pandas中为我们提供了isnull命令,可以非常方便的识别缺失值。

但如何处理缺失值,就需要根据实际情况讨论了。

如果仅有少量数据,可以使用df.isnull()快速的查看缺失值:

#首先创建一个包含缺失值的pd.Series作为例子string_data =pd.Series(['aardvark', 'artichoke', np.nan, 'avocado'])#接着使用isnull()函数查看空值是否存在string_data.isnull()

输出结果如下:




python dft Pythondf提前数据_python均值插补法填补缺失值


输出结果表明string_data[2]为空值

但在实际应用中,数据的量往往较大,直接查看的方式效率会很低。

此时,我们就可以依靠数据可视化来完成缺失数据的识别:

#以kaggle平台中房价预测项目数据为例,已创建了名为df_train的DataFrame#将缺失值按照柱状图的形式呈现,方便直观的观察哪些变量有缺失值及缺失的量有多少#统计各变量缺失数据总和missingTotal = df_train.isnull().sum()#仅选取有缺失的变量missingExist = missingTotal[missingTotal > 0]#将有缺失的变量按降序排列missingExist.sort_values(inplace=True)#将排好的数据以柱状图呈现f, ax = plt.subplots(figsize = (12, 9))missingExist.plot.bar()


python dft Pythondf提前数据_python df 列替换_02


缺失值按升序排列

完成缺失值识别后则需要进行缺失值处理,此时需要首先完成对变量的理解,确认缺失的原因,排除标记误解(如数据收集过程中可能用NA表示没有,但python理解为缺失)。尝试从源头完成缺失值补足,如若失败的情况下,才开始考虑统计手段。

统计学中,常用的缺失值处理手段主要包含删除、填补

1.删除

删除手段主要应用于数据缺失很少或很多的极端情况。删除命令常使用pandas中的dropna()完成。

  • 删除缺失值所在行:数据缺失较少,且数据分布较为均匀,不适用众数、均值补足
#删除所有含缺失值的行df.dropna()#默认how = 'any'#删除所有值均为缺失值的行df.dropna(how = 'all')#删除有效值小于等于x的行df.dropna(thresh = x)#删除对应列(以A列为例)的空值对应行:df.drop(df.loc[df['A'].isnull()].index)
  • 删除缺失值所在列(即删除对应变量):变量数据缺失量较大无法补足,且无标识误解
#删除所有有缺失值的列df.dropna(axis=1, how='all')#删除有效值小于等于x的列df.dropna(axis=1, thresh = x)

2.填补

从数据包含的广度、建模的可靠度角度来看,在尽可能的情况下,都应优先考虑填补。

不同的缺失情况,应考虑不同的填补方式。

首先,应优先排除标识误解情况,即根据数据说明,数据源中变量用NA代表无或0的情况。

#将标识误解列的NA替换为‘NO’或有意义的对应值df['A'].fillna('NO/obj', inplace = True)

在不存在误解的情况下,补足主要采用均值法/众数法

#数值类变量以均值法为主df['A'].fillna(df['A'].mean(), inplace = True)#分类变量以众数为主df['B'].fillna(df['B'].mode()[0], inplace = True)#[0]表示选取众数。

其他不常用补足法:

#用前后值补足:df.fillna(method = 'ffill', inplace = True)#前值df.fillna(method = 'bfill', inplace = True)#后值#可增加limt = x 限制补足个数

完成missing value删除/填补后,应检查是否还有missing value 存在

#缺失值按列汇总,结果应为0missingCheck = df.isnull().sum()missingCheck

#2重复值

重复值处理通常较为简单,仅需识别后进行删除处理即可。

一般而言,对一行中所有变量值进行重复值识别。仅所有变量都相同的,为重复。

#重复值识别,按行展示df.duplicated()#如果数据很多,则可选择展示重复值行df[df.duplicated()]


python dft Pythondf提前数据_python均值插补法填补缺失值_03


df.duplicated()的少量数据的重复值识别示例

完成重复值识别后,对重复值进行删除处理

df.drop_duplicates()

如果需要对某一列/几列进行重复值删除,可在drop_duplicates中表明,展示如下:

#某一列中的重复值df.drop_duplicates('A')#某几列中的重复组合#keep 默认为保留前一个有效值(index),'last'则为后值的indexdf.drop_duplicates(['A','B'], keep= 'last')

#3异常值

异常值处理也相对简单,通常识别后进行删除处理

识别方式主要有两种,绝对值和散点图可视化

1.绝对值识别主要用于纯数值类的异常值识别

#首先看数值的分布及范围,主要观察极值与均值关系df.describe()#用绝对值筛选出异常值,x为筛选范围,根据describe结果判断,在根据输出进一步判断#也可以用排序sort_values,效果相近df[(np.abs(df)>x).any(1)]

2.或者进行可视化识别,制作散点图观察

散点图观察法较为直观,但需要逐一制图。

#将dataFrame中想要观察的自变量与因变量组成新的DataFrame,用于散点图sp = pd.concat([df['A'],df['B']], axis = 1)sp.plot.scatter(x= 'A', y='B')


python dft Pythondf提前数据_缺失值_04


散点图查看异常值示例,右下角2点面积大售价低,为明显的异常值

#4数据转换

数据转换可分为替换原值以及创造新值2种情况

  • 替换原值可分为单值单替换,多值单替换,多值多替换三种情况,在单列上进行
#单值替换dfSeries.replace('obj', 'obj1')#多值单替换dfSeries.replace(['obj', 'obj1'], 'obj3')#多值多替换list法dfSeries.replace(['obj', 'obj1'], ['obj2', 'obj3'])#多值多替换dict法dfSeries.replace({'obj': 'obj2', 'obj1': 'obj3'})
  • 创造新值(列):基于原值创造新变量
#创建DataFrame作为基础data = pd.DataFrame({'food': ['bacon', 'pulled pork', 'bacon', 'pastrami', 'corned beef', 'bacon', 'pastrami', 'honey ham', 'nova lox'],                     'ounces': [4, 3, 12, 6, 7.5, 8, 3, 5, 6]})#以原DataFrame中某一变量值为key,创建Dictionary,用于创建新对应值#此示例中为'food'变量中食物名称作为识别Keymeat_to_animal = {'bacon': 'pig', 'pulled pork': 'pig', 'pastrami':'cow', 'corned beef': 'cow', 'honey ham': 'pig', 'nova lox': 'salmon'}#使用map创造新变量 'animal'标识肉来源动物data['animal'] = data['food'].map(meat_to_animal)

#5行列名称更改

在某些情况下,可能会将行列的index 名称更改为更容易理解/合适的名称

#创建示例data = pd.DataFrame(np.arange(12).reshape(3,4),                   index = ['Ohio', 'Colorado', 'New York'],                   columns=['one', 'two', 'three', 'four'])

转换列名:

#转换index名称,利用map函数data.index.map(lambda x: x[:4].upper())#[:4]为str的字母数量,限定名称长度#第二种方式 ,使用rename函数data.rename(index = str.title, columns = str.upper)#index首字母大写,列名全大写#rename with dictionarydata.rename( index = {'Ohio': 'INDIANA'},           columns = {'three': 'peekaboo'})

#6离散分箱

用于将离散的数值变量分箱,用于进一步分析或转换为分类变量

#可对list,np.array,pd.Series使用ages =pd.Series([20, 22, 25, 27, 21, 23, 37, 31, 61, 45, 41, 32])#分箱点设置bins = [18, 25, 35, 60, 100]#age Series分箱结果,显示每个值对应的分箱结果cats = pd.cut(ages, bins, right=False) #默认right =True,即包含右值#对应分箱结果,可以将数值类变量转化为分类变量#创建命名list,元素数量与分箱数量一一对应groupNames = ['Youth', 'YoungAdult', 'MiddleAged', 'Senior']#基于分箱结果的新分类变量pd.cut(ages, bins, labels = groupNames)


python dft Pythondf提前数据_python dft_05


将ages从年龄转化为年龄段分类

也可以对变量进行等额分箱,保证每个分箱区间大小一致

#创建np.array用于分箱data =np.random.randn(20)#如果不指定分箱点,指定分箱数量,则按照固定大小分箱,precision 为小数点后位数cat = pd.cut(data, 4, precision = 2)

还可以对变量进行等比例分箱

1.列明分箱数量,保证每个分箱中变量数量一致

#还可以按照分布百分比分隔,等分仅需要列明数量,使用qcut函数cats = pd.qcut(data, 4)

2.列明百分比区分点,进行百分比分箱

cats = pd.qcut(data, [0.1, 0.2, 0.5, 0.7, 0.9, 1])

#7随机取样

随机取样函数可将数列进行随机重排/部分随机取样

#创建DataFramedf = pd.DataFrame(np.arange(x * y).reshape(x,y))#随机重新排列 permutation函数,创建reindex列,以行为准sampler = np.random.permutation(x)#reindexingdf.take(sampler)

#8分类变量转换(Dummy variables)

对于不存在排序关系的分类变量,需要将分类变量转化为哑变量进行分析

#将DataFrame中的某一变量进行哑变量转换pd.get_dummies(df['key'])#对于变量数量多,且分类变量均需要转化为哑变量的情况,可以整体统一转化df = pd.get_dummies(df)

来源:知乎、python大数据

特许全球金融科技师CGFT(一级)

项目介绍


python dft Pythondf提前数据_缺失值_06


python dft Pythondf提前数据_python 用0补足两位_07


python dft Pythondf提前数据_python 用0补足两位_08


python dft Pythondf提前数据_python dft_09


python dft Pythondf提前数据_缺失值_10


python dft Pythondf提前数据_python均值插补法填补缺失值_11


python dft Pythondf提前数据_缺失值_12


python dft Pythondf提前数据_python 用0补足两位_13


python dft Pythondf提前数据_缺失值_14


python dft Pythondf提前数据_python 用0补足两位_15


python dft Pythondf提前数据_缺失值_16


python dft Pythondf提前数据_缺失值_17


python dft Pythondf提前数据_python均值插补法填补缺失值_18