小男孩‘自慰网亚洲一区二区,亚洲一级在线播放毛片,亚洲中文字幕av每天更新,黄aⅴ永久免费无码,91成人午夜在线精品,色网站免费在线观看,亚洲欧洲wwwww在线观看

分享

python/pandas數(shù)據(jù)挖掘(十四)

 imelee 2017-03-16

groupby

import pandas as pd
df = pd.DataFrame({'key1':list('aabba'),
                  'key2': ['one','two','one','two','one'],
                  'data1': np.random.randn(5),
                  'data2': np.random.randn(5)})
df
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6

這里寫(xiě)圖片描述

grouped=df['data1'].groupby(df['key1'])
grouped.mean()
  • 1
  • 2

以上的分組鍵均為Series,實(shí)際上分組鍵可以是任何長(zhǎng)度適當(dāng)?shù)臄?shù)組

states=np.array(['Ohio','California','California','Ohio','Ohio'])
years=np.array([2005,2005,2006,2005,2006])
df['data1'].groupby([states,years]).mean()
  • 1
  • 2
  • 3

這里寫(xiě)圖片描述

df.groupby('key1').mean()
  • 1

這里寫(xiě)圖片描述

可以看出沒(méi)有key2列,因?yàn)閐f[‘key2’]不是數(shù)值數(shù)據(jù),所以被從結(jié)果中移除。默認(rèn)情況下,所有數(shù)值列都會(huì)被聚合,雖然有時(shí)可能被過(guò)濾為一個(gè)子集。

對(duì)分組進(jìn)行迭代

for name, group in df.groupby('key1'):
        print (name)
        print (group)
  • 1
  • 2
  • 3

這里寫(xiě)圖片描述

可以看出name就是groupby中的key1的值,group就是要輸出的內(nèi)容。
同理:

for (k1,k2),group in df.groupby(['key1','key2']):
    print ('===k1,k2:')
    print (k1,k2)
    print ('===k3:')
    print (group)
  • 1
  • 2
  • 3
  • 4
  • 5

這里寫(xiě)圖片描述

對(duì)group by后的內(nèi)容進(jìn)行操作,如轉(zhuǎn)換成字典

piece=dict(list(df.groupby('key1')))
piece

{'a':       data1     data2 key1 key2
 0 -0.233405 -0.756316    a  one
 1 -0.232103 -0.095894    a  two
 4  1.056224  0.736629    a  one, 'b':       data1     data2 key1 key2
 2  0.200875  0.598282    b  one
 3 -1.437782  0.107547    b  two}


piece['a']
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12

這里寫(xiě)圖片描述

groupby默認(rèn)是在axis=0上進(jìn)行分組的,通過(guò)設(shè)置也可以在其他任何軸上進(jìn)行分組.

grouped=df.groupby(df.dtypes, axis=1)
dict(list(grouped))

{dtype('float64'):       data1     data2
 0 -0.233405 -0.756316
 1 -0.232103 -0.095894
 2  0.200875  0.598282
 3 -1.437782  0.107547
 4  1.056224  0.736629, dtype('O'):   key1 key2
 0    a  one
 1    a  two
 2    b  one
 3    b  two
 4    a  one
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15

選取一個(gè)或者一組列

這里寫(xiě)圖片描述
對(duì)于大數(shù)據(jù),很多情況是只需要對(duì)部分列進(jìn)行聚合

df.groupby(['key1','key2'])[['data2']].mean()
  • 1
  • 2

這里寫(xiě)圖片描述

通過(guò)字典或者series進(jìn)行分組

people=pd.DataFrame(np.random.randn(5,5),
                   columns=list('abcde'),
                   index=['Joe','Steve','Wes','Jim','Travis'])

people.ix[2:3,['b','c']]=np.nan #設(shè)置幾個(gè)nan
people
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6

這里寫(xiě)圖片描述

已知列的分組關(guān)系

mapping={'a':'red','b':'red','c':'blue','d':'blue','e':'red','f':'orange'}

by_column=people.groupby(mapping,axis=1)

by_column.sum()
  • 1
  • 2
  • 3
  • 4
  • 5

這里寫(xiě)圖片描述

如果不加axis=1, 則只會(huì)出現(xiàn) a b c d e

Series 也一樣

map_series=pd.Series(mapping)
map_series

a       red
b       red
c      blue
d      blue
e       red
f    orange
dtype: object

people.groupby(map_series,axis=1).count()
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12

這里寫(xiě)圖片描述

通過(guò)函數(shù)進(jìn)行分組

相較于dic或者Series,python函數(shù)在定義分組關(guān)系映射時(shí)更有創(chuàng)意。任何被當(dāng)做分組鍵的函數(shù)都會(huì)在各個(gè)索引上被調(diào)用一次,其返回值就會(huì)被用作分組名稱。假設(shè)你按人名的長(zhǎng)度進(jìn)行分組,僅僅傳入len即可


people.groupby(len).sum() a b c d e 3 -1.308709 -2.353354 1.585584 2.908360 -1.267162 5 -0.688506 -0.187575 -0.048742 1.491272 -0.636704 6 0.110028 -0.932493 1.343791 -1.928363 -0.364745
  • 1
  • 2

將函數(shù)和數(shù)組、列表、字典、Series混合使用也不是問(wèn)題,因?yàn)槿魏螙|西都會(huì)最終轉(zhuǎn)換為數(shù)組

 key_list=['one','one','one','two','two'] people.groupby([len,key_list]).sum()
  • 1

根據(jù)索引級(jí)別進(jìn)行分組

層次化索引最方便的地方就在于他能夠根據(jù)索引級(jí)別進(jìn)行聚合。要實(shí)現(xiàn)該目的,通過(guò)level關(guān)鍵字出入級(jí)別編號(hào)或者名稱即可:

columns=pd.MultiIndex.from_arrays([['US','US','US','JP','JP'],[1,3,5,1,3]],names=['cty','tenor'])
hier_df=pd.DataFrame(np.random.randn(4,5),columns=columns)
hier_df
  • 1
  • 2
  • 3

這里寫(xiě)圖片描述

hier_df.groupby(level='cty',axis=1).count()
  • 1

這里寫(xiě)圖片描述

數(shù)據(jù)聚合

調(diào)用自定義的聚合函數(shù)

這里寫(xiě)圖片描述

這里寫(xiě)圖片描述

面向列的多函數(shù)應(yīng)用

對(duì)Series或者DataFrame列的聚合運(yùn)算實(shí)際是使用aggregate或者調(diào)用mean,std等方法。下面我們想對(duì)不同的列使用不同的聚合函數(shù),或者一次應(yīng)用多個(gè)函數(shù)

grouped=tips.groupby(['sex','smoker'])
grouped_pct=grouped['tip_pct'] #tip_pct列
grouped_pct.agg('mean')#對(duì)與9-1圖標(biāo)中描述的統(tǒng)計(jì),可以將函數(shù)名直接以字符串傳入

#如果傳入一組函數(shù),得到的df的列名就會(huì)以相應(yīng)的函數(shù)命名
  • 1
  • 2
  • 3
  • 4
  • 5

這里寫(xiě)圖片描述

自動(dòng)給出的列名辨識(shí)度低,如果傳入的是(name, function)元組組成的列表,則各個(gè)元組的第一個(gè)元素將被用作df的列名

這里寫(xiě)圖片描述

對(duì)于df,可以定義一組用于全部列的函數(shù),或在不同的列應(yīng)用不同的函數(shù)
這里寫(xiě)圖片描述

如果想對(duì)不同的列應(yīng)用不同的函數(shù), 具體的辦法是想agg傳入一個(gè)從列名映射到函數(shù)的字典
這里寫(xiě)圖片描述
只有將多個(gè)函數(shù)應(yīng)用到至少一列時(shí),df才能擁有層次化的列

分組級(jí)運(yùn)算和轉(zhuǎn)換

聚合只是分組運(yùn)算的一種,它是數(shù)據(jù)轉(zhuǎn)換的特列。transform 和apply更牛叉.

transform會(huì)將一個(gè)函數(shù)應(yīng)用到各個(gè)分組,然后將結(jié)果放在適當(dāng)?shù)奈恢? 如果各分組產(chǎn)生的標(biāo)量值,則該標(biāo)量值會(huì)被廣播出去。

transform也是有嚴(yán)格條件的特殊函數(shù):傳入的函數(shù)只能產(chǎn)生兩種結(jié)果,要么產(chǎn)生一個(gè)可以廣播的標(biāo)量值(如:np.mean), 要么產(chǎn)生一個(gè)相同大小的結(jié)果數(shù)組。

people=pd.DataFrame(np.random.randn(5,5),
                   columns=list('abcde'),
                   index=['Joe','Steve','Wes','Jim','Travis'])
people
  • 1
  • 2
  • 3
  • 4
  • 5

這里寫(xiě)圖片描述

key=['one','two','one','two','one']
people.groupby(key).mean()
  • 1
  • 2

這里寫(xiě)圖片描述

people.groupby(key).transform(np.mean)
  • 1

這里寫(xiě)圖片描述

可以看到有很多與表2一樣的值。

def demean(arr):
    return arr-arr.mean()

demeaned=people.groupby(key).transform(demean)
demeaned
  • 1
  • 2
  • 3
  • 4
  • 5
demeaned.groupby(key).mean()
  • 1

最一般化的groupby 方法是apply.

tips=pd.read_csv('C:\\Users\\ecaoyng\\Desktop\\work space\\Python\\py_for_analysis_code\\pydata-book-master\\ch08\\tips.csv')
tips[:5]
  • 1
  • 2

這里寫(xiě)圖片描述

新生成一列

tips['tip_pct']=tips['tip']/tips['total_bill']
tips[:6]
  • 1
  • 2

這里寫(xiě)圖片描述

根據(jù)分組選出最高的5個(gè)tip_pct值

def top(df,n=5,column='tip_pct'):
    return df.sort_index(by=column)[-n:]
top(tips,n=6)
  • 1
  • 2
  • 3

這里寫(xiě)圖片描述

對(duì)smoker分組并應(yīng)用該函數(shù)

tips.groupby('smoker').apply(top)
  • 1

這里寫(xiě)圖片描述

多參數(shù)版本

tips.groupby(['smoker','day']).apply(top,n=1,column='total_bill')
  • 1

這里寫(xiě)圖片描述

分位數(shù)和桶分析

cut and qcut與groupby結(jié)合起來(lái),能輕松的對(duì)數(shù)據(jù)集的桶(bucket)或者分位數(shù)(quantile)分析。

frame=pd.DataFrame({'data1':np.random.randn(1000),
                   'data2': np.random.randn(1000)})
frame[:5]
  • 1
  • 2
  • 3

這里寫(xiě)圖片描述

factor=pd.cut(frame.data1,4)
factor[:10]

0    (0.281, 2.00374]
1    (0.281, 2.00374]
2    (-3.172, -1.442]
3     (-1.442, 0.281]
4    (0.281, 2.00374]
5    (0.281, 2.00374]
6     (-1.442, 0.281]
7     (-1.442, 0.281]
8     (-1.442, 0.281]
9     (-1.442, 0.281]
Name: data1, dtype: category
Categories (4, object): [(-3.172, -1.442] < (-1.442, 0.281] < (0.281, 2.00374] < (2.00374, 3.727]]
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
def get_stats(group):
    return {'min':group.min(),'max':group.max(),'count':group.count(),'mean':group.mean()}
grouped=frame.data2.groupby(factor)
grouped.apply(get_stats).unstack()
  • 1
  • 2
  • 3
  • 4

這里寫(xiě)圖片描述

這些都是長(zhǎng)度相等的桶,要根據(jù)樣本分為數(shù)得到大小相等的桶,使用qcut即可.

長(zhǎng)度相等的桶:區(qū)間大小相等
大小相等的桶:數(shù)據(jù)點(diǎn)數(shù)量相等

grouping=pd.qcut(frame.data1,10,labels=False)#label=false即可值獲取分位數(shù)的編號(hào)
grouped=frame.data2.groupby(grouping)
grouped.apply(get_stats).unstack()
  • 1
  • 2
  • 3

這里寫(xiě)圖片描述

    本站是提供個(gè)人知識(shí)管理的網(wǎng)絡(luò)存儲(chǔ)空間,所有內(nèi)容均由用戶發(fā)布,不代表本站觀點(diǎn)。請(qǐng)注意甄別內(nèi)容中的聯(lián)系方式、誘導(dǎo)購(gòu)買等信息,謹(jǐn)防詐騙。如發(fā)現(xiàn)有害或侵權(quán)內(nèi)容,請(qǐng)點(diǎn)擊一鍵舉報(bào)。
    轉(zhuǎn)藏 分享 獻(xiàn)花(0

    0條評(píng)論

    發(fā)表

    請(qǐng)遵守用戶 評(píng)論公約

    類似文章 更多