| 摘自Reuven Lerner的《Pandas锻炼》。 这篇文章讨论了在Pandas中使用数据框架。 |
打35%的折扣 潘达斯训练在manning.com结账时在折扣代码框中输入fcclerner2。
在pandas ,人们使用和想要使用的主要数据结构是数据框架。数据框架是二维的表格,看起来和工作原理类似于Excel电子表格。行是可以通过索引访问的。因此,只要你使用.loc 和.iloc ,通过索引检索元素,你就可以了。
但当然,数据框架也有列,每列都有一个名字。每一列实际上是它自己的系列,这意味着它有一个独立于其他列的dtype 。

图1.一个简单的数据框架,有五行 ('row0' 到'row4') 和五列 ('col0' 到'col4')
在一个典型的数据框架中,每一列代表我们数据的一个特征,或属性,而每一行代表一个样本。因此,在一个描述公司雇员的数据框架中,每个雇员有一行,有名字、姓氏、身份证号码、电子邮件地址和工资等列。
在这篇文章中,我们将练习在不同的环境中使用数据框架。我们将练习创建、修改、选择和更新数据框架。我们还将看到,几乎所有的系列方法都可以在数据框架上工作,每个数据框架列返回一个值。
有用的参考资料
| 概念
|
它是什么?
|
例子
|
要了解更多
| | --- | --- | --- | --- | |
s.loc
|
通过标签或布尔数组访问一个系列的元素
|
s.loc['a']
|
pandas.pydata.org/pandas-docs…
| |
s.iloc
|
通过位置访问系列中的元素
|
s.iloc[0]
|
pandas.pydata.org/pandas-docs…
| |
s.quantile
|
获取数值中某一百分比的数值
|
s.quantile(0.25)
|
pandas.pydata.org/pandas-docs…
| |
pd.concat
|
将两个数据框架连接起来
|
df = pd.concat([df, new_products])
|
pandas.pydata.org/pandas-docs…
| |
df.query
|
编写一个类似SQL的查询
|
df.query('v > 300')
|
pandas.pydata.org/pandas-docs…
| |
pd.read_csv
|
返回一个基于单列文件的新系列
|
s = pd.read_csv('filename.csv', squeeze=True)
|
pandas.pydata.org/pandas-docs…
| |
interpolate
|
返回一个新的数据框,其中有NaN 的数值插值
|
df = df.interpolate()
|
pandas.pydata.org/pandas-docs…
|
花括号还是点?
当我们在处理一个系列时,我们可以通过几种不同的方式来检索数值。使用索引(和loc ),使用位置(和iloc ),以及使用普通的方括号,这基本上等同于loc 。
当我们处理数据框架时,我们必须使用loc 或iloc 。这是因为方括号是指列。如果你试图通过索引检索一个行,使用方括号,你会得到一个错误信息,说没有这样的列存在。
因此,许多人习惯于使用方括号来检索列,这并不奇怪。通常情况下,我们会把列名作为方括号内的一个字符串来传递。比如说
df['a']
❶ 返回一个系列,列名是 a 。
❷ 返回一个系列,列名'first name' 。注意,列名包含一个空格。
❷返回一个双列的数据框,列 a 和 b ,从 df 。
❹ 返回 行 'c' 到 'd' , 包括在内。
注意上面的最后一个例子。方括号总是指列,而不是指行。除非你给他们传递一个分片,在这种情况下,他们看的是行。如果你想检索多列,那么你必须使用漂亮的索引。你不能使用片断。
所有这些都很好,但事实证明,还有另一种方法来处理列,即 "点符号"。也就是说,如果你想从数据框df 中检索列colname ,你可以说df.colname 。
这种语法吸引了很多人,原因有很多。它更容易输入,它的字符更少,因此更容易阅读,而且它看起来更自然。
但也有理由不喜欢它。带有空格和其他非法的Python标识符的栏目将无法使用。我个人发现,要记住df.whatever 是一个名为whatever 的列,还是一个名为pandas 的方法whatever ,会很混乱。有这么多的pandas 方法需要记忆,我会接受任何可以得到的帮助。
我个人使用括号符号。如果你喜欢点符号,你会有一个好伙伴--但要意识到,有些地方你无法使用它。
练习8:净收入
对于许多在工作中使用pandas 的人来说,从头开始创建一个新的数据框架是很罕见的。你会从一个CSV文件中创建它,或者你会在一个现有的数据框架(或几个现有的系列)上进行一些转换。但有时你会需要创建一个新的数据框架,知道如何创建它是非常有用的。
在这个练习中,我想让你创建一个数据框,代表一家公司销售的五种不同的产品。对于每个产品,我们要知道产品的ID号(任何唯一的两位数的整数都可以),产品名称,批发价,零售价,以及该产品在上个月的销售数量。我们在这里只是编造,如果你一直想成为一个赚钱的星际飞船经销商,这是你的机会!你可以在这里找到你想要的。
这个练习的任务是计算你从所有这些销售中得到多少净收入。
讨论
这个任务的第一部分涉及创建一个新的数据框架。有很多方法可以做到这一点,包括。
- 列表/系列的列表,其中每个内部列表代表一行,列名按位置排列
- dict的列表,其中dict的键表示哪些列被设置为每一行
- dict of lists/series,其中dict键确定列名,然后垂直分配数值
- 二维NumPy数组
其中哪一个最合适取决于手头的任务。在这种情况下,由于我想创建和描述单个产品,我决定使用dict列表。
注意,由于字典的键,我不必定义或传递任何列名。而且索引是默认的位置索引,所以我不必设置它。
有了我的数据框架,我怎样才能计算出总收入呢?这就需要对于每个产品,我们从零售价中减去批发价,也就是净收入。
df['retail_price'] - df['wholesale_price']
在这里,我们正在检索系列df['retail_price'] ,并从其中减去系列df['wholesale_price'] 。因为这两个系列是相互平行的,具有相同的索引,减法将在每一行进行,并将返回一个具有相同索引的新系列,但它们之间有差异。
一旦我们有了这个数列,我们将用它乘以我们每个产品的销售数量。
(df['retail_price'] - df['wholesale_price']) * df['sales']
❶ 如果没有括号,*运算符会优先使用,从而破坏了计算。
这样就会产生一个新的系列,它与df 共享一个索引,但其数值代表每个产品的总销售额。我们可以用sum 的方法将其相加。
((df['retail_price'] - df['wholesale_price']) * df['sales']).sum()
现在我用圆括号表示我想对从这组操作中得到的系列调用求和,而不是直接对 df['sales']调用。
解决方案
df = DataFrame([{'product_id':23, 'name':'computer', 'wholesale_price': 500, 'retail_price':1000, 'sales':100}, {'product_id':96, 'name':'Python Workout', 'wholesale_price': 35, 'retail_price':75, 'sales':1000}, {'product_id':97, 'name':'Pandas Workout', 'wholesale_price': 35, 'retail_price':75, 'sales':500}, {'product_id':15, 'name':'banana', 'wholesale_price': 0.5, 'retail_price':1, 'sales':200}, {'product_id':87, 'name':'sandwich', 'wholesale_price': 3, 'retail_price':5, 'sales':300}, ])
((df['retail_price'] - df['wholesale_price']) * df['sales']).sum()
❶ 返回 110700
练习之外
- 在哪些产品上,我们的零售价是批发价的两倍以上?
- 该店从食品与电脑与书籍中赚了多少钱?(你可以只根据指数值进行检索,不需要更复杂的东西)。
- 因为你的商店生意很好,所以你能谈成商品批发价的30%折扣。计算新的净收入。
这篇文章就写到这里。如果你想看到更多,请在这里查看曼宁的liveBook平台上的书。
The postData Frames in Pandasappeared first onManning.
