Python for Data Analysis | pandas

将Series和DataFrame引入本地命名空间。

ipython --pylab

In [1]: from pandas import Series, DataFrame
In [2]: import pandas as pd

pandas的数据结构介绍

两个主要数据结构:Series和DataFrame。

Series是一种类似于一维数组的对象,它由一组数据(各种NumPy数据类型)以及一组与之相关的数据标签(即索引)组成。仅由一组数据即可产生最简单的Series。

In [3]: obj = Series([4, 7, -5, 3])

In [4]: obj
Out[4]:
0    4
1    7
2   -5
3    3
dtype: int64

Series的字符串表现形式为:索引在左边,值在右边。由于我们没有为数据指定索引,于是会自动创建一个0到N-1(N为数据的长度)的整数型索引。可以通过Series的values和index属性获取其数组表示形式和索引对象。

In [5]: obj.values
Out[5]: array([ 4,  7, -5,  3], dtype=int64)

In [6]: obj.index
Out[6]: RangeIndex(start=0, stop=4, step=1)

通常,我们希望所创建的Series带有一个可以对各个数据点进行标记的索引。

In [7]: obj2 = Series([4, 7, -5, 3], index=['d', 'b', 'a', 'c'])

In [8]: obj2
Out[8]:
d    4
b    7
a   -5
c    3
dtype: int64

In [9]: obj2.index
Out[9]: Index([u'd', u'b', u'a', u'c'], dtype='object')

与普通NumPy数组相比,可以通过索引的方式选取Series中的单个或一组值。

In [10]: obj2['a']
Out[10]: -5

In [11]: obj2['d'] = 6

In [12]: obj2[['c', 'a', 'd']]
Out[12]:
c    3
a   -5
d    6
dtype: int64

 NumPy数组运算(如:根据布尔型数组进行过滤、标量乘法、应用数学函数等)都会保留索引和值之间的链接。

In [13]: obj2
Out[13]:
d    6
b    7
a   -5
c    3
dtype: int64

In [14]: obj2[obj2 > 0]
Out[14]:
d    6
b    7
c    3
dtype: int64

In [15]: obj2 * 2
Out[15]:
d    12
b    14
a   -10
c     6
dtype: int64

In [16]: np.exp(obj2)
Out[16]:
d     403.428793
b    1096.633158
a       0.006738
c      20.085537
dtype: float64

还可以将Series看成是一个定长的有序字典,因为它是索引值到数据值的一个映射。它可以用在许多原本需要字典参数的函数中。

In [17]: 'b' in obj2
Out[17]: True

In [18]: 'e' in obj2
Out[18]: False

如果数据被存放在一个Python字典中,也可以直接通过这个字典来创建Series。

In [19]: sdata = {'Ohio': 35000, 'Texas': 71000, 'Oregon': 16000, 'Utah': 5000}

In [20]: obj3 = Series(sdata)

In [21]: obj3
Out[21]:
Ohio      35000
Oregon    16000
Texas     71000
Utah       5000
dtype: int64

如果只传入一个字典,则结果Series中的索引就是原字典的键(有序排列)。

In [22]: states = ['California', 'Ohio', 'Oregon', 'Texas']

In [23]: obj4 = Series(sdata, index=states)

In [24]: obj4
Out[24]:
California        NaN
Ohio          35000.0
Oregon        16000.0
Texas         71000.0
dtype: float64

在这个例子中,sdata中跟states索引相匹配的那3个值会被找出来并放到相应的位置上,但由于"California"所对应的sdata值找不到,所以其结果九尾NaN(即“非数字”,not a number),在pandas中,用于表示缺失或NA值。pandas的isnull和notnull函数可用于检测缺失数据。

In [25]: pd.isnull(obj4)
Out[25]:
California     True
Ohio          False
Oregon        False
Texas         False
dtype: bool

In [26]: pd.notnull(obj4)
Out[26]:
California    False
Ohio           True
Oregon         True
Texas          True
dtype: bool

Series也有类似的实例方法。

In [27]: obj4.isnull()
Out[27]:
California     True
Ohio          False
Oregon        False
Texas         False

对于许多应用而言,Series最重要的一个功能是:它在算术运算中会自动对齐不同索引的数据。

In [28]: obj3
Out[28]:
Ohio      35000
Oregon    16000
Texas     71000
Utah       5000
dtype: int64

In [29]: obj4
Out[29]:
California        NaN
Ohio          35000.0
Oregon        16000.0
Texas         71000.0
dtype: float64

In [30]: obj3 + obj4
Out[30]:
California         NaN
Ohio           70000.0
Oregon         32000.0
Texas         142000.0
Utah               NaN
dtype: float64

Series对象本身及其索引都有一个name属性,该属性跟pandas其它的关键功能关系非常密切。

In [31]: obj4.name = 'population'

In [32]: obj4.index.name = 'state'

In [33]: obj4
Out[33]:
state
California        NaN
Ohio          35000.0
Oregon        16000.0
Texas         71000.0
Name: population, dtype: float64

Series的索引可以通过赋值的方式就地修改。

In [34]: obj.index = ['Bob', 'Steve', 'Jeff', 'Ryan']

In [35]: obj
Out[35]:
Bob      4
Steve    7
Jeff    -5
Ryan     3
dtype: int64

DataFrame是一个表格型的数据结构,它含有一组有序的列,每列可以使不同的值类型(数值、字符串、布尔值等)。DataFrame既有行索引也有列索引,它可以被看做由Series组成的字典(共用同一个索引)。跟其他类型的数据结构相比(如:R的data.frame),DataFrame中面向行和面向列的操作基本上是平衡的。其实,DataFrame中的数据是以一个或多个二维块存放的(而不是列表、字典或别的一维数据结构)。

构建DataFrame的办法有很多,最常用的一种是直接传入一个由等长列表或NumPy数组组成的字典。

In [36]: data = {'state': ['Ohio', 'Ohio', 'Ohio', 'Nevada', 'Nevada'],
   ....:         'year': [2000, 2001, 2002, 2001, 2002],
   ....:         'pop': [1.5, 1.7, 3.6, 2.4, 2.9]}

In [37]: frame = DataFrame(data)

结果DataFrame会自动加上索引(跟Series一样),且全部列会被有序排列。

In [38]: frame
Out[38]:
   pop   state  year
0  1.5    Ohio  2000
1  1.7    Ohio  2001
2  3.6    Ohio  2002
3  2.4  Nevada  2001
4  2.9  Nevada  2002

如果指定了列序列,则DataFrame的列就会按照指定顺序进行排列。

In [39]: DataFrame(data, columns=['year', 'state', 'pop'])
Out[39]:
   year   state  pop
0  2000    Ohio  1.5
1  2001    Ohio  1.7
2  2002    Ohio  3.6
3  2001  Nevada  2.4
4  2002  Nevada  2.9

跟Series一样,如果传入的列在数据中找不到,就会产生NA值。

In [40]: frame2 = DataFrame(data, columns=['year', 'state', 'pop', 'debt'],
   ....:                    index=['one', 'two', 'three', 'four', 'five'])

In [41]: frame2
Out[41]:
       year   state  pop debt
one    2000    Ohio  1.5  NaN
two    2001    Ohio  1.7  NaN
three  2002    Ohio  3.6  NaN
four   2001  Nevada  2.4  NaN
five   2002  Nevada  2.9  NaN

In [42]: frame2.columns
Out[42]: Index([u'year', u'state', u'pop', u'debt'], dtype='object')

通过类似字典标记的方式或属性的方式,可以将DataFrame的列获取为一个Series。

In [43]: frame2['state']
Out[43]:
one        Ohio
two        Ohio
three      Ohio
four     Nevada
five     Nevada
Name: state, dtype: object

In [44]: frame2.year
Out[44]:
one      2000
two      2001
three    2002
four     2001
five     2002
Name: year, dtype: int64

注意,返回的Series拥有原DataFrame相同的索引,且其name属性也已经被相应地设置好了啦。行也可以通过位置或名称的方式进行获取,比如用索引字段loc (label based indexing)或iloc (positional indexing)。

In [45]: frame2.loc['three']
Out[45]:
year     2002
state    Ohio
pop       3.6
debt      NaN
Name: three, dtype: object

In [46]: frame2.iloc[3]
Out[46]:
year       2001
state    Nevada
pop         2.4
debt        NaN
Name: four, dtype: object

列可以通过赋值的方式进行修改。例如,可以给那个空的"debt"列赋上一个标量值或一组值。

In [47]: frame2['debt'] = 16.5

In [48]: frame2
Out[48]:
       year   state  pop  debt
one    2000    Ohio  1.5  16.5
two    2001    Ohio  1.7  16.5
three  2002    Ohio  3.6  16.5
four   2001  Nevada  2.4  16.5
five   2002  Nevada  2.9  16.5

In [49]: frame2['debt'] = np.arange(5.)

In [50]: frame2
Out[50]:
       year   state  pop  debt
one    2000    Ohio  1.5   0.0
two    2001    Ohio  1.7   1.0
three  2002    Ohio  3.6   2.0
four   2001  Nevada  2.4   3.0
five   2002  Nevada  2.9   4.0

将列表或数组赋值给某个列时,其长度必须跟DataFrame的长度相匹配。如果赋值的是一个Series,就会精确匹配DataFrame的索引,所有的空位都将被填上缺失值。

In [51]: val = Series([-1.2, -1.5, -1.7], index=['two', 'four', 'five'])

In [52]: frame2['debt'] = val

In [53]: frame2
Out[53]:
       year   state  pop  debt
one    2000    Ohio  1.5   NaN
two    2001    Ohio  1.7  -1.2
three  2002    Ohio  3.6   NaN
four   2001  Nevada  2.4  -1.5
five   2002  Nevada  2.9  -1.7

为不存在的列赋值会创建出一个新列。关键字del用于删除列。

In [54]: frame2['eastern'] = frame2.state == 'Ohio'

In [55]: frame2
Out[55]:
       year   state  pop  debt  eastern
one    2000    Ohio  1.5   NaN     True
two    2001    Ohio  1.7  -1.2     True
three  2002    Ohio  3.6   NaN     True
four   2001  Nevada  2.4  -1.5    False
five   2002  Nevada  2.9  -1.7    False

In [56]: del frame2['eastern']

In [57]: frame2.columns
Out[57]: Index([u'year', u'state', u'pop', u'debt'], dtype='object')

* 通过索引方式返回的列只是相应数据的视图而已,并不是副本。因此,对返回的Series所做的任何就地修改全都会反映到DataFrame上。通过Series的copy方法即可显示地复制列。

另一种常见的数据形式是嵌套字典(也就是字典的字典)。

In [58]: pop = {'Nevada': {2001: 2.4, 2002: 2.9},
   ....:        'Ohio': {2000: 1.5, 2001: 1.7, 2002: 3.6}}

如果将它传给DataFrame,它就会被解释为:外层字典的键作为列,内层键则作为行索引。

In [59]: frame3 = DataFrame(pop)

In [60]: frame3
Out[60]:
      Nevada  Ohio
2000     NaN   1.5
2001     2.4   1.7
2002     2.9   3.6

也可以对该结果进行转置。

In [61]: frame3.T
Out[61]:
        2000  2001  2002
Nevada   NaN   2.4   2.9
Ohio     1.5   1.7   3.6

内层字典的键会被合并、排序以形成最终的索引。如果显示指定了索引,则不会这样。

In [62]: DataFrame(pop, index=[2001, 2002, 2003])
Out[62]:
      Nevada  Ohio
2001     2.4   1.7
2002     2.9   3.6
2003     NaN   NaN

由Series组成的字典差不多也是一样的用法。

In [63]: pdata = {'Ohio': frame3['Ohio'][:-1],
   ....:          'Nevada': frame3['Nevada'][:2]}

In [64]: DataFrame(pdata)
Out[64]:
      Nevada  Ohio
2000     NaN   1.5
2001     2.4   1.7

原文地址:https://www.cnblogs.com/princemay/p/9045927.html