numpy中的ndarray與pandas的Series和DataFrame之間的區別
在資料分析中,經常涉及numpy中的ndarray物件與pandas的Series和DataFrame物件之間的轉換,讓大家產生困惑。本文將簡單介紹這三種資料型別,並以股票資訊為例,給出相關物件之間轉換的具體示例。
ndarray陣列物件
NumPy中的ndarray是一個多維陣列物件,該物件由兩部分組成:
- 實際的資料;
- 描述這些資料的元資料。
大部分的陣列操作僅僅修改元資料部分,而不改變底層的實際資料。NumPy陣列一般是同質的(但有一種特殊的陣列型別例外,它是異質的),即陣列中的所有元素型別必須是一致的。這樣有一個好處:如果我們知道陣列中的元素均為同一型別,該陣列所需的儲存空間就很容易確定下來。
我們舉一個簡單的多維陣列的例子。在這裡,我們使用Numpy提供的arange函式來來方便的建立一維陣列,其函式原型為arange([start,] stop[, step,], dtype=None)。可以指定起始值、結束值、步長及資料型別引數,這裡步長引數為整數值。如果要使用非整數值的步長,可以考慮使用linespace函式。通過reshape()函式將一維陣列轉換為多維陣列。
-
>>> import numpy as np
-
>>> a = np.arange(10).reshape(2,5)
-
>>> print a
-
[[0 1 2 3 4]
-
[5 6 7 8 9]]
-
>>> type(a)
-
<type 'numpy.ndarray'>
-
>>> a[0,1]
-
1
-
>>> a[0][1]
-
1
-
>>> a[:, ::2]
-
array([[0, 2, 4],
-
[5, 7, 9]])
-
>>> a[0]
-
array([0, 1, 2, 3, 4])
-
>>> a.shape
-
(2L, 5L)
-
>>> a.dtype
-
dtype('int32')
-
>>> a.dtype.itemsize
-
4
多維陣列的操作也非常簡單,可以參考list型別對陣列進行訪問、切片操作。比較重要的是可以通過shape屬性獲取陣列的維數。
我們也可以通過多維陣列來標識異構的資料型別,以股票資料為例,通過dtype類來定義資料型別物件stock, 其包括日期、開盤價、收盤價、最高價、最低價、成交量及股票編碼資訊:
-
from numpy import *
-
if __name__ == '__main__':
-
stock = dtype([('date', str_, 10), ('open', float32), ('close', float32),
-
('high', float32), ('low', float32), ('volume', float32),
-
('code', float32)])
-
data = array([("2017-10-18", 11.53, 11.69, 11.70, 11.51, 871365.0, "000001"),
-
("2017-10-19", 11.64, 11.63, 11.72, 11.57, 722764.0, "000001"),
-
("2017-10-20", 11.59, 11.48, 11.59, 11.41, 461808.0, "000001"),
-
("2017-10-23", 11.39, 11.19, 11.40, 11.15, 1074465.0, "000001")],
-
dtype=stock)
-
print type(data)
-
print data
顯示結果:
-
<type 'numpy.ndarray'>
-
[ ('2017-10-18', 11.52999973, 11.68999958, 11.69999981, 11.51000023, 871365., 1.)
-
('2017-10-19', 11.64000034, 11.63000011, 11.72000027, 11.56999969, 722764., 1.)
-
('2017-10-20', 11.59000015, 11.47999954, 11.59000015, 11.40999985, 461808., 1.)
-
('2017-10-23', 11.39000034, 11.18999958, 11.39999962, 11.14999962, 1074465., 1.)]
在實際應用中,我們很少使用ndarray來定義異構的資料型別,而是使用pandas中的Series和DataFrame來操作。
Series物件
從一般意義上來講, Series 可以簡單地被認為是一維的陣列。 Series 和一維陣列最主要的區別在於 Series 型別具有索引( index )。Series支援從列表和字典建立,這裡僅舉以列表建立的例子:
-
from pandas import Series
-
if __name__ == '__main__':
-
data = [
-
["2017-10-18", 11.53, 11.69, 11.70, 11.51, 871365.0, 000001],
-
["2017-10-19", 11.64, 11.63, 11.72, 11.57, 722764.0, 000001],
-
["2017-10-20", 11.59, 11.48, 11.59, 11.41, 461808.0, 000001],
-
["2017-10-23", 11.39, 11.19, 11.40, 11.15, 1074465.0, 000001]]
-
series = Series(data, index=['a', 'b', 'c', 'd'])
-
print series
-
#將Series轉換為ndarray型別
-
arr = series.as_matrix()
可以呼叫as_matrix()將其轉換為ndarray型別的物件。
DataFrame物件
DataFrame 是將數個 Series 按列合併而成的二維資料結構,每一列單獨取出來是一個 Series ,這和SQL資料庫中取出的資料是很類似的。所以,按列對一個 DataFrame 進行處理更為方便,使用者在程式設計時注意培養按列構建資料的思
維。 DataFrame 的優勢在於可以方便地處理不同型別的列,因此,就不要考慮如何對一個全是浮點數的 DataFrame 求逆之類的問題了,處理這種問題還是把資料存成NumPy的 matrix 型別比較便利一些。
我們仍平安銀行的例子,建立DataFrame物件,這裡把日期提取出來作為index,同時指定了列名。
-
from pandas import Series, DataFrame
-
from numpy import array
-
if __name__ == '__main__':
-
data = [
-
[11.53, 11.69, 11.70, 11.51, 871365.0, 000001],
-
[11.64, 11.63, 11.72, 11.57, 722764.0, 000001],
-
[11.59, 11.48, 11.59, 11.41, 461808.0, 000001],
-
[11.39, 11.19, 11.40, 11.15, 1074465.0, 000001]]
-
df = DataFrame(data, index=["2017-10-18", "2017-10-19", "2017-10-20", "2017-10-23"],
-
columns=["open", "close", "high", "low", "volume", "code"])
-
print df
-
print df.as_matrix(['open', 'close'])
-
print df.values
-
print array(df)
這裡,我們展示了3種方法將DataFrame獲取ndarray型別的方法。as_matrix()方法可以指定獲取的列;values屬性將使用所有的列轉換為ndarray物件,等同與無引數的as_matrix();array()接受將DataFrame物件作為引數建立ndarray物件。