干净整洁的数据是后续进行研究和分析的基础。数据科学家们会花费大量的时间来清理数据集,毫不夸张地说,数据清洗会占据他们80%的工作时间,而真正用来分析数据的时间只占到20%左右。
所以,数据清洗到底是在清洗些什么?
通常来说,你所获取到的原始数据不能直接用来分析,因为它们会有各种各样的问题,如包含无效信息,列名不规范、格式不一致,存在重复值,缺失值,异常值等.....
本文会给大家介绍如何用Python中自带的Pandas和NumPy库进行数据清洗。在正式讲解之前,先简单介绍一下这两个非常好用的库。
Pandas的名称来自于Panel data和Python数据分析data analysis,是Python的一个数据分析包,最初由AQR Capital Management于2008年4月开发,被作为金融数据分析工具,为时间序列分析提供了很好的支持,并于2009年底开源出来。
NumPy是Numeric Python的缩写,是Python的一种开源的数值计算扩展,可用来存储和处理大型矩阵matrix,比Python自身的嵌套列表结构要高效的多,提供了许多高级的数值编程工具,如:矩阵数据类型、矢量处理,以及精密的运算库,专为进行严格的数字处理而产生。
目录
一、了解数据
二、清洗数据
去除不需要的行、列
重新命名列
重新设置索引
用字符串操作规范列
用函数规范列
删除重复数据
填充缺失值
三、总结
【注】为了清晰直观地展示数据清洗操作,本文会用到几个不同的数据集,重点是方法的讲解。
【工具】Python 3
一、了解数据
拿到一个全新的数据集,应该从哪里入手?
没错,我们需要先了解数据,看看它长什么样子。这里用tushare.pro上面的日线行情数据进行展示,以浦发银行(600000.SH)为例。常用的方法和属性如下:
.head()
.tail()
.shape
.columns
.info()
.describe()
.value_counts()
首先,获取数据:
.head() 查看前n行数据,默认值是5
.tail() 查看后n行数据,默认值是5
.shape 查看数据维数
.columns 查看所有列名
.info() 查看索引、数据类型和内存信息
.describe() 查看每列数据的基本统计值,包括计数值、均值、标准差、最小最大值、1/4、1/2、3/4分位数。
.value_counts() 查看Series对象的唯一值和计数值
如果上面这些操作还不够直观的话,就作图看看,需要先导入Python可视化库matplotlib, 为了规范代码书写,统一写在了最前面。
① 直方图
② 箱型图
③ 散点图
二、清洗数据
了解数据集之后,我们就可以开始对数据集进行清洗了,前面提到通常要处理的问题有包含无效信息,列名不规范、格式不一致,存在重复值,缺失值,异常值等,下面我们一个一个来看。
01
去除不需要的行、列
在分析一个数据集的时候,很多信息其实是用不到的,因此,需要去除不必要的行或列。这里以csv文件为例,在导入的时候就可以通过设置pd.read_csv()里面的参数来实现这个目的。
先来感受一下官方文档中给出的详细解释,里面的参数是相当的多,本文只介绍比较常用的几个,感兴趣的话,可以好好研究一下文档,这些参数还是非常好用的,能省去很多导入后整理的工作。
【header】默认header=0,即将文件中的0行作为列名和数据的开头,但有时候0行的数据是无关的,我们想跳过0行,让1行作为数据的开头,可以通过将header设置为1来实现。
【usecols】根据列的位置或名字,如[0,1,2]或[‘a’, ‘b’, ‘c’],选出特定的列。
【nrows】要导入的数据行数,在数据量很大、但只想导入其中一部分时使用。
获取数据:
从NYC OpenData网站下载csv格式原始数据
数据样本如下:
导入数据,只选取前100行和特定几列。
再看一下将header设置为1的效果,但这里其实不需要这么做,因为0行数据是有用的。
如果在数据导入之后,还想删除某些行和列,可以用 .drop() 方法。
先创建一个列表list,把不需要的列名放进去,再调用.drop() 方法,参数axis为1时代表列,为0时代表行,参数inplace=True表示不创建新的对象,直接对原始对象进行修改。这里我们删除前两列。
02
重新命名列
当原始数据的列名不好理解,或者不够简洁时,可以用.rename()方法进行修改。这里我们把英文的列名改成中文,先创建一个字典,把要修改的列名定义好,然后调用rename()方法。
03
重新设置索引
数据默认的索引是从0开始的有序整数,但如果想把某一列设置为新的索引,可以用.set_index()方法实现,在示例中我们把"区"这列设置为新索引。
04
用字符串操作规范列
字符串str操作是非常实用的,因为列中总是会包含不必要的字符,常用的方法如下:
lower()
upper()
capitalize()
replace()
strip()
split()
get()
contains()
find()
str.lower() 是把大写转换成小写,同理,str.upper()是把小写转换成大写,将示例中用大写字母表示的索引转换成小写,效果如下:
str.capitalize() 设置首字母大写
str.replace('$', '') 替换特定字符。这里把列中的美元符号$去掉,替换成空字符。
str.strip() 去除字符串中的头尾空格、以及n t
str.split('x') 使用字符串中的'x'字符作为分隔符,将字符串分隔成列表。这里将列中的值以'.'进行分割,效果如下:
str.get() 选取列表中某个位置的值。接着上面分割后的结果,我们用str.get(0)取出列表中前一个位置的数值,生成新的一列“总附加费用_整数”,即取出金额中的整数部分。
str.contains() 判断是否存在某个字符,返回的是布尔值。这里判断一下"总附加费用_整数"列中是否包含字符'0'。
str.find()检测字符串中是否包含子字符串str,如果是,则返回该子字符串开始位置的索引值。示例中的'0'字符最开始出现的位置是1。
学完基本的字符串操作方法,我们来看一下如何结合NumPy来提高字符串操作的效率。
获取数据,这里我们用一个新的数据集,下载链接如下,里面包含两个csv文件和一个txt文件:
https://github.com/realpython/python-data-cleaning
① BL-Flickr-Images-Book.csv
② olympics.csv
③ university_towns.txt
导入csv文件①,先观察一下"Place of Publication"这一列。
我们发现,这一列中的格式并不统一,比如1行中的London; Virtue & Yorston,London后面的部分我们不需要,还有7行的pp. 40. G. Bryan & Co: Oxford, 1898,有效信息只是Oxford。
再用.tail(10)方法观察这一列的最后十行:
我们发现,8281行的Newcastle-upon-Tyne中间有连字符,但8285行却没有,这些都是要解决的格式不规范的问题。
为了清洗这一列,我们可以将Pandas中的.str()方法与NumPy的np.where函数相结合,np.where函数是Excel的IF()宏的矢量化形式,它的语法如下:
如果condition条件为真,则执行then,否则执行else。这里的condition条件可以是一个类数组的对象,也可以是一个布尔表达式,我们也可以利用np.where函数嵌套多个条件进行矢量化计算和判断。
下面的这个实例,就是同时嵌套两个条件解决上面提到的那两个字符串问题。思路是,如果字符串里面包含'London',就用'London'代替,这样可以去除其他冗余信息,否则,如果字符串里面包含'Oxford',则用'Oxford'代替,同时如果字符串里面包含符号'-',则用空格代替。
打印出前十行和后十行,结果如下,可以和整理前的数据进行对比。
05
用函数规范列
在某些情况下,数据不规范的情况并不局限于某一列,而是更广泛地分布在整个表格中。因此,自定义函数并应用于整个表格中的每个元素会更加高效。用applymap()方法可以实现这个功能,它类似于内置的map()函数,只不过它是将函数应用于整个表格中的所有元素。
我们打开文件txt文件③,先观察一下数据:
观察发现,数据格式有如下特点:
州A[edit]
城市A(大学)
城市B(大学)
州B[edit]
城市A(大学)
城市B(大学)
......
我们可以利用这一数据格式,创建一个(州、市)元组列表,并将该列表转化成一个DataFrame。先创建一个列表,列表中包含州和城市(大学)信息。
用pd.DataFrame()方法将这个列表转换成一个DataFrame,并将列设置为"State"和"RegionName"。Pandas将接受列表中的每个元素,并将元组左边的值传入"State"列,右边的值传入"RegionName"列。
接下来就要对列中的字符串进行整理,"State"列中的有效信息是州名,"RegionName"列中的有效信息是城市名,其他的字符都可以删掉。当然,除了用之前提到的利用循环和.str()方法相结合的方式进行操作,我们还可以选择用applymap()方法,它会将传入的函数作用于整个DataFrame所有行列中的每个元素。
先定义函数get_citystate(item),功能是只提取元素中的有效信息。
然后,我们将这个函数传入applymap(),并应用于towns_df,结果如下:
现在towns_df表格看起来是不是干净多了!
06
删除重复数据
重复数据会消耗不必要的内存,在处理数据时执行不必要的计算,还会使分析结果出现偏差。因此,我们有必要学习如何删除重复数据。
先看一个来自DataCamp的数据集,调用info()方法打印出每列数据的具体信息和内存信息,共有24092行数据,内存占用量是753.0+ KB。
下面调用.drop_duplicates()函数删除重复数据。
删完之后我们发现,数据量减少到了317个,内存占用缩减至12.4+ KB。
07
填充缺失值
数据集中经常会存在缺失值,学会正确处理它们很重要,因为在计算的时候,有些无法处理缺失值,有些则在默认情况下跳过缺失值。而且,了解缺失的数据,并思考用什么值来填充它们,对做出无偏的数据分析至关重要。
同样是来自DataCamp的一个存在缺失值的数据集:
以"Ozone"列为例,我们可以调用fillna()函数,用该列的均值.mean()填充NaN值。
三、总结
了解如何进行数据清洗非常重要,因为它是数据科学的重要组成部分。好在Python提供了非常好用的Pandas和NumPy库来帮助我们清理数据集,本文介绍的方法都是在实际中经常会用到的,希望大家能牢记于心。
本篇文章来源于: 菜鸟学Python
本文为原创文章,版权归知行编程网所有,欢迎分享本文,转载请保留出处!
你可能也喜欢
- ♥ Python写SQL出现乱码的解决方法12/15
- ♥ 如何使用python编译器10/29
- ♥ 如何在 python 中使用注释?12/11
- ♥ 灵魂拷问:学Python搞一个云服务器到底能干嘛?08/07
- ♥ python字符串是如何存储的11/02
- ♥ 如何比较python时间09/09
内容反馈