我是熊猫的新手。我不太了解它,所以请放轻松我。 我试图用线图在2009年到2013年绘制A区和B区的面积与火的频率。我想出了如何导入.csv文件,但我有问题分组系列和创建图形。 我的csv文件如下所示:
Date, Area, NaturalDisaster
12/10/2009, A, Fire
12/13/2009, B, Flood
01/12/2010, B, Fire
05/01/2011, A, Fire
30/11/2012, B, Flood
14/03/2013, B, Fire
那么请你帮我开始吧。我将不胜感激任何帮助。 谢谢。
答案 0 :(得分:2)
您可以使用pandas.DataFrame.groupby
对pandas中的数据进行分组。
groupby
和类似函数背后的主要思想是"Split - Apply - Combine",一般来说,你:
要获得A区和B区内发生的火灾频率,您必须先选择火灾而不是洪水的行,您可以使用boolean indexing执行此操作:
df[df['NaturalDisaster']=='Fire']
然后,您需要根据区域(A或B)进行分组(或拆分)。您只需使用groupby('Area')
即可完成此操作。将其添加到上一行代码中会变为:
df[df['NaturalDisaster']=='Fire'].groupby('Area')
最后在pandas中你需要apply some aggregate function到你的小组(申请阶段),我们将使用count()
来计算结果数量。然后这一行成为:
df[df['NaturalDisaster']=='Fire'].groupby('Area').count()
但是有一个问题。此结果有两列,其中包含完全相同的数字。那是因为我们计算了Date
列和NaturalDisaster
列。这个重复的信息可能很烦人,所以我们在进行计数时只需要一列。最后一行成为
areas = df[df['NaturalDisaster']=='Fire'].groupby('Area')['NaturalDisaster'].count()
我们现在已经计算了A区和B区发生的火灾事故,但理想情况下我们想要频率。我们可以通过除以sum(areas)
:
areas /= sum(areas)
我们现在有一个数据框,其中包含A区和B区的火灾事故频率。我们可以plot this as a bar chart只使用
areas.plot(kind='bar')
将所有代码组合成一堆,它变为:
from io import StringIO
import pandas as pd
import matplotlib.pyplot as plt
s = '''Date, Area, NaturalDisaster
12/10/2009, A, Fire
12/13/2009, B, Flood
01/12/2010, B, Fire
05/01/2011, A, Fire
30/11/2012, B, Flood
14/03/2013, B, Fire'''
df = pd.read_csv(StringIO(s), sep=',\s+', engine='python')
# Ignore everything above this part, it's simply creating your dataframe.
areas = df[df['NaturalDisaster']=='Fire'].groupby('Area')['NaturalDisaster'].count()
areas /= sum(areas)
areas.plot(kind='bar')
plt.show()
最后,我使用groupby回答了这个问题,因为你特意询问了它,但是你也可以使用pandas.pivot_table
来做同样的操作(以及同样强大的东西)。使用areas
创建pivot_table
数据框就像是
areas = pd.pivot_table(df[df['NaturalDisaster']=='Fire'],
values='NaturalDisaster',
index='Area',
aggfunc='count')
然后,您将继续使用上面给出的相同代码。