Pandas使用一個二維的數據結構DataFrame來表示表格式的數據,相比較於Numpy,Pandas能夠存儲混合的數據結構,同時使用NaN來表示缺失的數據,而不用像Numpy同樣要手工處理缺失的數據,而且Pandas使用軸標籤來表示行和列python
一、文件讀取
首先將用到的pandas和numpy加載進來
import pandas as pd
import numpy as np
讀取數據:
#csv和xlsx分別用read_csv和read_xlsx,下面以csv爲例git
df=pd.read_csv('f:\1024.csv') github
一般來講,數據是CSV格式,就算不是,至少也能夠轉換成CSV格式。在Python中,咱們的操做以下:web
import pandas as pd算法
# Reading data locallyapi
df = pd.read_csv('/Users/al-ahmadgaidasaad/Documents/d.csv')數組
# Reading data from web數據結構
data_url = "https://raw.githubusercontent.com/alstat/Analysis-with-Programming/master/2014/Python/Numerical-Descriptions-of-the-Data/data.csv"dom
df = pd.read_csv(data_url)
爲了讀取本地CSV文件,咱們須要pandas這個數據分析庫中的相應模塊。
其中的read_csv函數可以讀取本地和web數據。
# Head of the data
print df.head()
# OUTPUT
Abra Apayao Benguet Ifugao Kalinga
0 1243 2934 148 3300 10553
1 4158 9235 4287 8063 35257
2 1787 1922 1955 1074 4544
3 17152 14501 3536 19607 31687
4 1266 2385 2530 3315 8520
# Tail of the data
print df.tail()
# OUTPUT
Abra Apayao Benguet Ifugao Kalinga
74 2505 20878 3519 19737 16513
75 60303 40065 7062 19422 61808
76 6311 6756 3561 15910 23349
77 13345 38902 2583 11096 68663
78 2623 18264 3745 16787 16900
上述操做等價於經過print(head(df))來打印數據的前6行,以及經過print(tail(df))來打印數據的後6行。
固然Python中,默認打印是5行,而R則是6行。所以R的代碼head(df, n = 10),
在Python中就是df.head(n = 10),打印數據尾部也是一樣道理。
在Python中,咱們則使用columns和index屬性來提取,以下:
# Extracting column names
print df.columns
# OUTPUT
Index([u'Abra', u'Apayao', u'Benguet', u'Ifugao', u'Kalinga'], dtype='object')
# Extracting row names or the index
print df.index
# OUTPUT
Int64Index([0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30], dtype='int64')
數據轉置使用T方法,
# Transpose data
print df.T
# OUTPUT
0 1 2 3 4 5 6 7 8 9
Abra 1243 4158 1787 17152 1266 5576 927 21540 1039 5424
Apayao 2934 9235 1922 14501 2385 7452 1099 17038 1382 10588
Benguet 148 4287 1955 3536 2530 771 2796 2463 2592 1064
Ifugao 3300 8063 1074 19607 3315 13134 5134 14226 6842 13828
Kalinga 10553 35257 4544 31687 8520 28252 3106 36238 4973 40140
... 69 70 71 72 73 74 75 76 77
Abra ... 12763 2470 59094 6209 13316 2505 60303 6311 13345
Apayao ... 37625 19532 35126 6335 38613 20878 40065 6756 38902
Benguet ... 2354 4045 5987 3530 2585 3519 7062 3561 2583
Ifugao ... 9838 17125 18940 15560 7746 19737 19422 15910 11096
Kalinga ... 65782 15279 52437 24385 66148 16513 61808 23349 68663
78
Abra 2623
Apayao 18264
Benguet 3745
Ifugao 16787
Kalinga 16900
其餘變換,例如排序就是用sort屬性。如今咱們提取特定的某列數據。
Python中,可使用iloc或者ix屬性。可是我更喜歡用ix,由於它更穩定一些。假設咱們需數據第一列的前5行,咱們有:
print df.ix[:, 0].head()
# OUTPUT
0 1243
1 4158
2 1787
3 17152
4 1266
Name: Abra, dtype: int64
順便提一下,Python的索引是從0開始而非1。爲了取出從11到20行的前3列數據,咱們有:
print df.ix[10:20, 0:3]
# OUTPUT
Abra Apayao Benguet
10 981 1311 2560
11 27366 15093 3039
12 1100 1701 2382
13 7212 11001 1088
14 1048 1427 2847
15 25679 15661 2942
16 1055 2191 2119
17 5437 6461 734
18 1029 1183 2302
19 23710 12222 2598
20 1091 2343 2654
上述命令至關於df.ix[10:20, ['Abra', 'Apayao', 'Benguet']]。
爲了捨棄數據中的列,這裏是列1(Apayao)和列2(Benguet),咱們使用drop屬性,以下:
print df.drop(df.columns[[1, 2]], axis = 1).head()
# OUTPUT
Abra Ifugao Kalinga
0 1243 3300 10553
1 4158 8063 35257
2 1787 1074 4544
3 17152 19607 31687
4 1266 3315 8520
axis 參數告訴函數到底捨棄列仍是行。若是axis等於0,那麼就捨棄行。
統計描述
下一步就是經過describe屬性,對數據的統計特性進行描述:
print df.describe()
# OUTPUT
Abra Apayao Benguet Ifugao Kalinga
count 79.000000 79.000000 79.000000 79.000000 79.000000
mean 12874.379747 16860.645570 3237.392405 12414.620253 30446.417722
std 16746.466945 15448.153794 1588.536429 5034.282019 22245.707692
min 927.000000 401.000000 148.000000 1074.000000 2346.000000
25% 1524.000000 3435.500000 2328.000000 8205.000000 8601.500000
50% 5790.000000 10588.000000 3202.000000 13044.000000 24494.000000
75% 13330.500000 33289.000000 3918.500000 16099.500000 52510.500000
max 60303.000000 54625.000000 8813.000000 21031.000000 68663.000000
Python有一個很好的統計推斷包。那就是scipy裏面的stats。ttest_1samp實現了單樣本t檢驗。所以,若是咱們想檢驗數據Abra列的稻穀產量均值,經過零假設,這裏咱們假定整體稻穀產量均值爲15000,咱們有:
from scipy import stats as ss
# Perform one sample t-test using 1500 as the true mean
print ss.ttest_1samp(a = df.ix[:, 'Abra'], popmean = 15000)
# OUTPUT
(-1.1281738488299586, 0.26270472069109496)
返回下述值組成的元祖:
t : 浮點或數組類型
t統計量
prob : 浮點或數組類型
two-tailed p-value 雙側機率值
經過上面的輸出,看到p值是0.267遠大於α等於0.05,所以沒有充分的證聽說平均稻穀產量不是150000。將這個檢驗應用到全部的變量,一樣假設均值爲15000,咱們有:
print ss.ttest_1samp(a = df, popmean = 15000)
# OUTPUT
(array([ -1.12817385, 1.07053437, -65.81425599, -4.564575 , 6.17156198]),
array([ 2.62704721e-01, 2.87680340e-01, 4.15643528e-70,
1.83764399e-05, 2.82461897e-08]))
第一個數組是t統計量,第二個數組則是相應的p值。
可視化
Python中有許多可視化模塊,最流行的當屬matpalotlib庫。稍加說起,咱們也可選擇bokeh和seaborn模塊。以前的博文中,我已經說明了matplotlib庫中的盒須圖模塊功能。
# Import the module for plotting
import matplotlib.pyplot as plt
plt.show(df.plot(kind = 'box'))
如今,咱們能夠用pandas模塊中集成R的ggplot主題來美化圖表。要使用ggplot,咱們只須要在上述代碼中多加一行,
import matplotlib.pyplot as plt
pd.options.display.mpl_style = 'default' # Sets the plotting display theme to ggplot2
df.plot(kind = 'box')
# Import the seaborn library
import seaborn as sns
# Do the boxplot
plt.show(sns.boxplot(df, widths = 0.5, color = "pastel"))
import numpy as np
import scipy.stats as ss
def case(n = 10, mu = 3, sigma = np.sqrt(5), p = 0.025, rep = 100):
m = np.zeros((rep, 4))
for i in range(rep):
norm = np.random.normal(loc = mu, scale = sigma, size = n)
xbar = np.mean(norm)
low = xbar - ss.norm.ppf(q = 1 - p) * (sigma / np.sqrt(n))
up = xbar + ss.norm.ppf(q = 1 - p) * (sigma / np.sqrt(n))
if (mu > low) & (mu < up):
rem = 1
else:
rem = 0
m[i, :] = [xbar, low, up, rem]
inside = np.sum(m[:, 3])
per = inside / rep
desc = "There are " + str(inside) + " confidence intervals that contain "
"the true mean (" + str(mu) + "), that is " + str(per) + " percent of the total CIs"
return {"Matrix": m, "Decision": desc}
import numpy as np
import scipy.stats as ss
def case2(n = 10, mu = 3, sigma = np.sqrt(5), p = 0.025, rep = 100):
scaled_crit = ss.norm.ppf(q = 1 - p) * (sigma / np.sqrt(n))
norm = np.random.normal(loc = mu, scale = sigma, size = (rep, n))
xbar = norm.mean(1)
low = xbar - scaled_crit
up = xbar + scaled_crit
rem = (mu > low) & (mu < up)
m = np.c_[xbar, low, up, rem]
inside = np.sum(m[:, 3])
per = inside / rep
desc = "There are " + str(inside) + " confidence intervals that contain "
"the true mean (" + str(mu) + "), that is " + str(per) + " percent of the total CIs"
return {"Matrix": m, "Decision": desc}
Pandas使用函數read_csv()來讀取csv文件
import pandas food_info = ('food_info.csv') print(type(food_info))
# 輸出:<class 'pandas.core.frame.DataFrame'> 可見讀取後變成一個DataFrame變量
該文件的內容以下:
使用函數head( m )來讀取前m條數據,若是沒有參數m,默認讀取前五條數據
first_rows = food_info.head() first_rows = food_info.head(3)
因爲DataFrame包含了不少的行和列,
Pandas使用省略號(...)來代替顯示所有的行和列,可使用colums屬性來顯示所有的列名
print(food_info.columns)
# 輸出:輸出所有的列名,而不是用省略號代替
Index(['NDB_No', 'Shrt_Desc', 'Water_(g)', 'Energ_Kcal', 'Protein_(g)', 'Lipid_Tot_(g)', 'Ash_(g)', 'Carbohydrt_(g)', 'Fiber_TD_(g)', 'Sugar_Tot_(g)', 'Calcium_(mg)', 'Iron_(mg)', 'Magnesium_(mg)', 'Phosphorus_(mg)', 'Potassium_(mg)', 'Sodium_(mg)', 'Zinc_(mg)', 'Copper_(mg)', 'Manganese_(mg)', 'Selenium_(mcg)', 'Vit_C_(mg)', 'Thiamin_(mg)', 'Riboflavin_(mg)', 'Niacin_(mg)', 'Vit_B6_(mg)', 'Vit_B12_(mcg)', 'Vit_A_IU', 'Vit_A_RAE', 'Vit_E_(mg)', 'Vit_D_mcg', 'Vit_D_IU', 'Vit_K_(mcg)', 'FA_Sat_(g)', 'FA_Mono_(g)', 'FA_Poly_(g)', 'Cholestrl_(mg)'], dtype='object')
可使用tolist()函數轉化爲list
food_info.columns.tolist()
與Numpy同樣,用shape屬性來顯示數據的格式
dimensions = food_info.shapeprint(dimensions) print(dimensions)
輸出:(8618,36) , 其中dimensions[0]爲8618,dimensions[1]爲36
與Numpy同樣,用dtype屬性來顯示數據類型,Pandas主要有如下幾種dtype:
object -- 表明了字符串類型
int -- 表明了整型
float -- 表明了浮點數類型
datetime -- 表明了時間類型
bool -- 表明了布爾類型
當讀取了一個文件以後,Pandas會經過分析值來推測每一列的數據類型
print()
輸出:每一列對應的數據類型
NDB_No int64
Shrt_Desc object
Water_(g) float64
Energ_Kcal int64
Protein_(g) float64
...
讀取了文件後,Pandas會把文件的一行做爲列的索引標籤,使用行數字做爲行的索引標籤
注意,行標籤是從數字0開始的
Pandas使用Series數據結構來表示一行或一列的數據,相似於Numpy使用向量來表示數據。Numpy只能使用數字來索引,而Series可使用非數字來索引數據,當你選擇返回一行數據的時候,Series並不只僅返回該行的數據,同時還有每一列的標籤的名字。
譬如要返回文件的第一行數據,Numpy就會返回一個列表(但你可能不知道每個數字究竟表明了什麼)
而Pandas則會同時把每一列的標籤名返回(此時就很清楚數據的意思了)
Pandas使用loc[]方法來選擇行的數據
# 選擇單行數據: food_info.loc[0] # 選擇行標號爲0的數據,即第一行數據 food_info.loc[6] # 選擇行標號爲6的數據,即第七行數據 # 選擇多行數據: food_info.loc[3:6] # 使用了切片,注意:因爲這裏使用loc[]函數,因此返回的是行標號爲3,4,5,6的數據,與python的切片不一樣的是這裏會返回最後的標號表明的數據,但也可使用python的切片方法:food_info[3:7] food_info.loc[[2,5,10]] # 返回行標號爲2,5,10三行數據 練習:返回文件的最後五行 方法一: length = food_info.shape[0] last_rows = food_info.loc[length-5:length-1] 方法二: num_rows = food_info.shape[0] last_rows = food_info[num_rows-5:num_rows] Pandas直接把列名稱填充就能返回該列的數據 ndb_col = food_info["NDB_No"] # 返回列名稱爲NDB_No的那一列的數據 zinc_copper = food_info[["Zinc_(mg)", "Copper_(mg)"]] # 返回兩列數據
如今要按照以下公式計算全部食物的健康程度,並按照降序的方式排列結果:
Score=2×(Protein_(g))−0.75×(Lipid_Tot_(g))
對DataFrame中的某一列數據進行算術運算,實際上是對該列中的全部元素進行逐一的運算,譬如:
water_energy = food_info["Water_(g)"] * food_info["Energ_Kcal"]
原理:
因爲每一列的數據跨度太大,有的數據是從0到100000,而有的數據是從0到10,因此爲了儘可能減小數據尺度對運算結果的影響,採起最簡單的方法來規範化數據,那就是將每一個數值都除以該列的最大值,從而使全部數據都處於0和1之間。其中max()函數用來獲取該列的最大值.
food_info['Normalized_Protein'] = food_info['Protein_(g)'] / food_info['Protein_(g)'].max() food_info['Normalized_Fat'] = food_info['Lipid_Tot_(g)'] / food_info['Lipid_Tot_(g)'].max() food_info['Norm_Nutr_Index'] = food_info["Normalized_Protein"] * 2 - food_info["Normalized_Fat"] * 0.75 注意:上面的兩個語句已經在原來的DataFrame中添加了三列,列名分別爲Normalized_Protein和Normalized_Fat,Norm_Nutr_Index。只須要使用中括號和賦值符就能添加新列,相似於字典 對DataFrame的某一列數據排序,只須要使用函數sort()便可 food_info.sort("Sodium_(mg)") # 函數參數爲列名,默認是按照升序排序,同時返回一個新的 DataFramefood_info.sort("Norm_Nutr_Index", inplace=True, ascending=False ) # 經過inplace參數來控制在原表排序,而不是返回一個新的對象;ascending參數用來控制是否升序排序
import pandas as pd
read_csv()
讀寫csv數據
df =
pd.read_csv(path)
: 讀入csv文件,造成一個數據框(data.frame)
df = pd.read_csv(path, header=None)
不要把第一行做爲header
to_csv()
* 注意,默認會將第一行做爲header,而且默認會添加index,因此不須要的話須要手動禁用 *
df.to_csv(path, header=False, index=False)
df.head(1) 讀取頭幾條數據
df.tail(1) 讀取後幾條數據
df[‘date’] 獲取數據框的date列
df.head(1)[‘date’] 獲取第一行的date列
df.head(1)[‘date’][0] 獲取第一行的date列的元素值
sum(df[‘ability’]) 計算整個列的和
df[df[‘date’] == ‘20161111’] 獲取符合這個條件的行
df[df[‘date’] == ‘20161111’].index[0] 獲取符合這個條件的行的行索引的值
df.iloc[1] 獲取第二行
df.iloc[1][‘test2’] 獲取第二行的test2值
10 mins to pandas
df.index 獲取行的索引
df.index[0] 獲取第一個行索引
df.index[-1] 獲取最後一個行索引,只是獲取索引值
df.columns 獲取列標籤
df[0:2] 獲取第1到第2行,從0開始,不包含末端
df.loc[1] 獲取第二行
df.loc[:,’test1’] 獲取test1的那一列,這個冒號的意思是全部行,逗號表示行與列的區分
df.loc[:,[‘test1’,’test2’]] 獲取test1列和test2列的數據
df.loc[1,[‘test1’,’test2’]] 獲取第二行的test1和test2列的數據
df.at[1,’test1’] 表示取第二行,test1列的數據,和上面的方法相似
df.iloc[0] 獲取第一行
df.iloc[0:2,0:2] 獲取前兩行前兩列的數據
df.iloc[[1,2,4],[0,2]] 獲取第1,2,4行中的0,2列的數據
(df[2] > 1).any() 對於Series應用any()方法來判斷是否有符合條件的
能夠經過 Data Structure Intro Setion 來查看有關該節內容的詳細信息。
一、能夠經過傳遞一個list對象來建立一個Series,pandas會默認建立整型索引:
二、經過傳遞一個numpy array,時間索引以及列標籤來建立一個DataFrame:
三、經過傳遞一個可以被轉換成相似序列結構的字典對象來建立一個DataFrame:
四、查看不一樣列的數據類型:
五、若是你使用的是IPython,使用Tab自動補全功能會自動識別全部的屬性以及自定義的列,下圖中是全部可以被自動識別的屬性的一個子集:
詳情請參閱:Basics Section
一、 查看frame中頭部和尾部的行:
二、 顯示索引、列和底層的numpy數據:
三、 describe()函數對於數據的快速統計彙總:
四、 對數據的轉置:
五、 按軸進行排序
六、 按值進行排序
雖然標準的Python/Numpy的選擇和設置表達式都可以直接派上用場,可是做爲工程使用的代碼,咱們推薦使用通過優化的pandas數據訪問方式: .at, .iat, .loc, .iloc 和 .ix詳情請參閱Indexing and Selecing Data 和 MultiIndex / Advanced Indexing。
l 獲取
一、 選擇一個單獨的列,這將會返回一個Series,等同於df.A:
二、 經過[]進行選擇,這將會對行進行切片
l 經過標籤選擇
一、 使用標籤來獲取一個交叉的區域
二、 經過標籤來在多個軸上進行選擇
三、 標籤切片
四、 對於返回的對象進行維度縮減
五、 獲取一個標量
六、 快速訪問一個標量(與上一個方法等價)
l 經過位置選擇
一、 經過傳遞數值進行位置選擇(選擇的是行)
二、 經過數值進行切片,與numpy/python中的狀況相似
三、 經過指定一個位置的列表,與numpy/python中的狀況相似
四、 對行進行切片
五、 對列進行切片
六、 獲取特定的值
l 布爾索引
一、 使用一個單獨列的值來選擇數據:
二、 使用where操做來選擇數據:
三、 使用isin()方法來過濾:
l 設置
一、 設置一個新的列:
二、 經過標籤設置新的值:
三、 經過位置設置新的值:
四、 經過一個numpy數組設置一組新值:
上述操做結果以下:
五、 經過where操做來設置新的值:
在pandas中,使用np.nan來代替缺失值,這些值將默認不會包含在計算中,詳情請參閱:Missing Data Section。
一、 reindex()方法能夠對指定軸上的索引進行改變/增長/刪除操做,這將返回原始數據的一個拷貝:、
二、 去掉包含缺失值的行:
三、 對缺失值進行填充:
四、 對數據進行布爾填充:
詳情請參與 Basic Section On Binary Ops
統計(相關操做一般狀況下不包括缺失值)
一、 執行描述性統計:
二、 在其餘軸上進行相同的操做:
三、 對於擁有不一樣維度,須要對齊的對象進行操做。Pandas會自動的沿着指定的維度進行廣播:
Apply
一、 對數據應用函數:
直方圖
具體請參照:Histogramming and Discretization
字符串方法
Series對象在其str屬性中配備了一組字符串處理方法,能夠很容易的應用到數組中的每一個元素,以下段代碼所示。更多詳情請參考:Vectorized String Methods.
Pandas提供了大量的方法可以輕鬆的對Series,DataFrame和Panel對象進行各類符合各類邏輯關係的合併操做。具體請參閱:Merging section
Concat
Join 相似於SQL類型的合併,具體請參閱:Database style joining
Append 將一行鏈接到一個DataFrame上,具體請參閱Appending:
對於」group by」操做,咱們一般是指如下一個或多個操做步驟:
(Splitting)按照一些規則將數據分爲不一樣的組;
(Applying)對於每組數據分別執行一個函數;
(Combining)將結果組合到一個數據結構中;
詳情請參閱:Grouping section
一、 分組並對每一個分組執行sum函數:
二、 經過多個列進行分組造成一個層次索引,而後執行函數:
詳情請參閱 Hierarchical Indexing 和 Reshaping。
Stack
數據透視表,詳情請參閱:Pivot Tables.
能夠從這個數據中輕鬆的生成數據透視表:
Pandas在對頻率轉換進行從新採樣時擁有簡單、強大且高效的功能(如將按秒採樣的數據轉換爲按5分鐘爲單位進行採樣的數據)。這種操做在金融領域很是常見。具體參考:Time Series section。
一、 時區表示:
二、 時區轉換:
三、 時間跨度轉換:
四、 時期和時間戳之間的轉換使得可使用一些方便的算術函數。
從0.15版本開始,pandas能夠在DataFrame中支持Categorical類型的數據,詳細 介紹參看:categorical introduction和API documentation。
一、 將原始的grade轉換爲Categorical數據類型:
二、 將Categorical類型數據重命名爲更有意義的名稱:
三、 對類別進行從新排序,增長缺失的類別:
四、 排序是按照Categorical的順序進行的而不是按照字典順序進行:
五、 對Categorical列進行排序時存在空的類別:
具體文檔參看:Plotting docs
對於DataFrame來講,plot是一種將全部列及其標籤進行繪製的簡便方法:
CSV,參考:Writing to a csv file
一、 寫入csv文件:
二、 從csv文件中讀取:
HDF5,參考:HDFStores
一、 寫入HDF5存儲:
二、 從HDF5存儲中讀取:
Excel,參考:MS Excel
一、 寫入excel文件:
二、 從excel文件中讀取: