Pandas的Categorical Data
http://liao.cpython.org/pandas15/
- Docs »
- Pandas的Categorical Data类型
15. Pandas的Categorical Data
pandas从0.15版开始提供分类数据类型,用于表示统计学里有限且唯一性数据集,例如描述个人信息的性别一般就男和女两个数据常用'm'和'f'来描述,有时也能对应编码映射为0和1。血型A、B、O和AB型等选择可以映射为0、1、2、3这四个数字分别代表各个血型。pandas里直接就有categorical类型,可以有效地对数据进行分组进行相应的汇总统计工作。
当DataFrame的某列(字段)上的数据值是都是某有限个数值的集合里的值的时候,例如:性别就男和女,有限且唯一。这列可以采用Categorical Data类型来存储、统计。
pandas的Categorical Data类型灵感来源于Data wareHorsing数据仓库里的维度表设计理念,即某列数据存储的不是数据本身,而是该数据对应的编码(有称为分类、字典编码) 这些编码比数据本身存储依赖的空间小,但能基于编码统计汇总的速度要比数据本身的存储、统计速度要快。
15.1 如何理解Categorical Data?
下面看一张某水果超市的供货商表(表1):
供货商 | 水果 | 价格 |
---|---|---|
1 | apple | 5.20 |
2 | pearl | 3.50 |
3 | orange | 7.30 |
5 | apple | 5.00 |
6 | orange | 7.50 |
7 | orange | 7.30 |
9 | apple | 5.20 |
4 | pearl | 3.70 |
8 | orange | 7.30 |
第2列是各个水果供应商的能供应的水果类型,目前市场也就apple、pearl、orange
三种水果可以买到,对于一个大超市而言可能这个表很长、有很多的水果供应商,假设有1亿条数据,那么数据存储所需空间主要浪费在水果名字上了,其他字段都是数值型的数据,而水果这一列是字符串型的,很占空间,如何能降低这张大表的存储空间浪费呢? 设计一个辅助的水果编码表(表2):
编码 | 水果 |
---|---|
0 | apple |
1 | pearl |
2 | orange |
那么供应商的表就变为(表3):
供货商 | 水果 | 价格 |
---|---|---|
1 | 0 | 5.20 |
2 | 1 | 3.50 |
3 | 2 | 7.30 |
5 | 0 | 5.00 |
6 | 2 | 7.50 |
7 | 2 | 7.30 |
9 | 0 | 5.20 |
4 | 1 | 3.70 |
8 | 2 | 7.30 |
变化后的表的数据存储所需的空间量就下来了。也就是说在供应商表里存储的不是水果名数据本身而是存储的水果对应的编码值(通常用整形数据)。可以查供应商表里水果的编码再查辅助的编码表找到水果名。这个水果的编码表在数据仓库里称为维度表(dimension tables)。 而pandas的categorical data的作用就是构建并依赖这个维度表,即例子里的水果编码表。pandas里维度表里记录着若干且唯一的几个分类,可以通过categorical数据的categories 属性获得而数据的所一一对应的编码可以通过codes获得。
编码 | 水果 |
---|---|
0 | apple |
1 | pearl |
2 | orange |
当DataFrame里的某列数据采用categorical Data方式,那么这列数据的存储会大大降低。
import pandas as pd
import time
idx = [1,2,3,5,6,7,9,4,8]
name = ["apple","pearl","orange", "apple","orange","orange","apple","pearl","orange"]
price = [5.20,3.50,7.30,5.00,7.50,7.30,5.20,3.70,7.30]
df = pd.DataFrame({ "fruit": name , "price" : price}, index = idx)
print df,"\n"
print df.memory_usage(),"\n"
print df.dtypes
print "*" * 20
df['fruit'] = df['fruit'].astype('category')
print df
print df.memory_usage(),"\n"
print df.dtypes
程序的执行结果:
fruit price
1 apple 5.2
2 pearl 3.5
3 orange 7.3
5 apple 5.0
6 orange 7.5
7 orange 7.3
9 apple 5.2
4 pearl 3.7
8 orange 7.3
fruit 72
price 72
dtype: int64
fruit object
price float64
dtype: object
********************
fruit price
1 apple 5.2
2 pearl 3.5
3 orange 7.3
5 apple 5.0
6 orange 7.5
7 orange 7.3
9 apple 5.2
4 pearl 3.7
8 orange 7.3
fruit 33
price 72
dtype: int64
fruit category
price float64
dtype: object
最初创建的DataFrame变量df的各个列的类型:
fruit object
price float64
dtype: object
经语句df['fruit'] = df['fruit'].astype('category')
将fruit列由Series改为了category类型。
fruit category
price float64
dtype: object
请注意fruit列的类型的变化。正是因为fruit采用了category类型,其存储所需的空间由之前的
fruit 72
price 72
dtype: int64
变为
fruit 33
price 72
dtype: int64
即72变为33,变化了,尽管原始的DataFrame数据量不大,所以变化比率也不大。读者可以适当加大df的数据长度,可以看到很明显的存储容量的降低。
import pandas as pd
import time
idx = [1,2,3,5,6,7,9,4,8]
name = ["apple","pearl","orange", "apple","orange","orange","apple","pearl","orange"]
price = [5.20,3.50,7.30,5.00,7.50,7.30,5.20,3.70,7.30]
#df = pd.DataFrame({ "fruit": name , "price" : price}, index = idx)
N = 100000
df = pd.DataFrame({ "fruit": name * N, "price" : price * N}, index = idx * N)
print df[:4]
print df.memory_usage(),"\n"
print df.dtypes
print "*" * 20
df['fruit'] = df['fruit'].astype('category')
print df[:4]
print df.memory_usage(),"\n"
print df.dtypes
执行结果:
fruit price
1 apple 5.2
2 pearl 3.5
3 orange 7.3
5 apple 5.0
fruit 7200000
price 7200000
dtype: int64
fruit object
price float64
dtype: object
********************
fruit price
1 apple 5.2
2 pearl 3.5
3 orange 7.3
5 apple 5.0
fruit 900024
price 7200000
dtype: int64
fruit category
price float64
dtype: object
15.2 理解category
总结一下pandas的category数据,两次打印DataFrame数据df的结果都是一样的,但是第二次打印的df是其fruit列经语句df['fruit'] = df['fruit'].astype('category')
改变了其数据类型已不是Series而是category类型,该列存储所需的内存使用容量大大降低。
import pandas as pd
import time
idx = [1,2,3,5,6,7,9,4,8]
name = ["apple","pearl","orange", "apple","orange","orange","apple","pearl","orange"]
price = [5.20,3.50,7.30,5.00,7.50,7.30,5.20,3.70,7.30]
#df = pd.DataFrame({ "fruit": name , "price" : price}, index = idx)
N = 1
df = pd.DataFrame({ "fruit": name * N, "price" : price * N}, index = idx * N)
df['fruit'] = df['fruit'].astype('category')
print df,"\n"
print "df.price.values\n", df.price.values,"\n"
print "df.fruit.values\n", df.fruit.values, "\n"
print "df.fruit.values.codes\n",df.fruit.values.codes, "\n"
print "df.fruit.values.categories\n",df.fruit.values.categories, "\n"
fruit列是category类型的,通过codes和categorie组合出fruit的values。
fruit price
1 apple 5.2
2 pearl 3.5
3 orange 7.3
5 apple 5.0
6 orange 7.5
7 orange 7.3
9 apple 5.2
4 pearl 3.7
8 orange 7.3
df.price.values
[5.2 3.5 7.3 5. 7.5 7.3 5.2 3.7 7.3]
df.fruit.values
[apple, pearl, orange, apple, orange, orange, apple, pearl, orange]
Categories (3, object): [apple, orange, pearl]
df.fruit.values.codes
[0 2 1 0 1 1 0 2 1]
df.fruit.values.categories
Index([u'apple', u'orange', u'pearl'], dtype='object')
values对应于表1里的第2列即显示输出时“水果”,codes对应于表3的第2列即存储时“水果”列,categories对应于表2的“水果”列即有限唯一的一个集合。
15.3 总结
Categorical Data数据由codes和categories组成,categories是有限且唯一的分类集合,codes是原数据对应的分类的编码, Categorical Data不要求有限并唯一。
Pandas的Categorical Data的更多相关文章
- Pandas的Categorical Data类型
pandas从0.15版开始提供分类数据类型,用于表示统计学里有限且唯一性数据集,例如描述个人信息的性别一般就男和女两个数据常用'm'和'f'来描述,有时也能对应编码映射为0和1.血型A.B.O和AB ...
- Categorical Data
This is an introduction to pandas categorical data type, including a short comparison with R's facto ...
- pandas的Categorical方法
对于数据样本的标签,如果我们事先不知道这个样本有多少类别,那么可以对数据集的类别列进行统计,这时我们用pandas的Categorical方法就非常快的实现. 1.说明: 你的数据最好是一个serie ...
- 【跟着stackoverflow学Pandas】“Large data” work flows using pandas-pandas大数据处理流程
最近做一个系列博客,跟着stackoverflow学Pandas. 以 pandas作为关键词,在stackoverflow中进行搜索,随后安照 votes 数目进行排序: https://stack ...
- [论文]A Link-Based Cluster Ensemble Approach for Categorical Data Clustering
http://www.cnblogs.com/Azhu/p/4137131.html 这篇论文建议先看了上面这一遍,两篇作者是一样的,方法也一样,这一片论文与上面的不同点在于,使用的数据集是目录数据, ...
- 吴裕雄--天生自然python学习笔记:pandas模块读取 Data Frame 数据
读取行数据 读取一个列数据的语法为: 例如,读取所有学生自然科目的成绩 : import pandas as pd datas = [[65,92,78,83,70], [90,72,76,93,56 ...
- Pandas Python For Data Science
- Pandas分类
Pandas分类 categorical data是指分类数据:数据类型为:男女.班级(一班.二班).省份(河北.江苏等),若使用赋值法给变量赋值,例如(男=1,女=0),数字1,0之间没有大小之分, ...
- pandas入门10分钟——serries其实就是data frame的一列数据
10 Minutes to pandas This is a short introduction to pandas, geared mainly for new users. You can se ...
随机推荐
- 使用SAP Cloud Platform Leonardo机器学习的测试控制台
选中一个需要进行测试的Leonardo机器学习服务,点击Configure Environments: 因为我不想使用sandbox环境,所以我选择了eu10这个region: 维护clientid和 ...
- Thymeleaf 模板
Thymeleaf 模板布局 th:fragment.th:replace.th:insert.th:remove th:fragment 模板布局 模板片段说明 模板中,经常希望从其他模板中包含⼀ ...
- GitHub开源的10个超棒后台管理面板
目录1.AdminLTE 2.vue-Element-Admin 3.tabler 4.Gentelella 5.ng2-admin 6.ant-design-pro 7.blur-admin 8.i ...
- 使用VisualGDB和OpenOCD调试STM32L0开发板
本教程主要介绍如何配置VisualGDB和OpenOCD来调试STM32L0开发板的固件,使微控制器进入睡眠模式. 我们将创建一个NUCLEO-L031K6开发板的基本工程,并介绍当CPU进入休眠模式 ...
- IoC与DI的理解
首先要分享的是Iteye的开涛这位技术牛人对Spring框架的IOC的理解,写得非常通俗易懂,以下内容全部来自原文,原文地址:http://jinnianshilongnian.iteye.com/b ...
- 实例演示MaxTenuringThreshold参数及阈值动态调整策略
在上一次[https://www.cnblogs.com/webor2006/p/11031563.html]学习了一个新的JVM对象晋升到老年代的参数“MaxTenuringThreshold”,它 ...
- MySQL进阶10--DML数据操纵预言: insert/delete/update --多表连接修改/.多表连接删除/多表连接查询-- truncate 和 delete的区别
/* DML -- 数据操纵预言: insert/delete/update */ #一: 插入语句 /* 语法1: insert into 表名(列名,..,列名....) values(值1,值2 ...
- 使用Topshelf创建Windows服务[转载]
概述 Topshelf是创建Windows服务的另一种方法,老外的一篇文章Create a .NET Windows Service in 5 steps with Topshelf通过5个步骤详细的 ...
- leetcode-cn上面刷题
https://leetcode-cn.com/problemset/database/ ------------------------------------------------------- ...
- Springboot与ActiveMQ、Solr、Redis中分布式事物的初步探索
Springboot与ActiveMQ.Solr.Redis中分布式事物的初步探索 解决的场景:事物中的异步问题,当要求数据库与solr服务器的最终一致时. 程序条件: 利用消息队列,当数据库添加成功 ...