效率驚人!三大相見恨晚的Pandas函數(shù)
本文轉(zhuǎn)載自公眾號“讀芯術(shù)”(ID:AI_Discovery)
數(shù)據(jù)科學(xué)領(lǐng)域如此之廣,鮮少有人能精通所有語言、數(shù)據(jù)庫,筆者盡管已經(jīng)從事了該行業(yè)數(shù)年之久,但仍然所知不多。學(xué)無止境,變得優(yōu)秀的方法就是不停下學(xué)習(xí)的腳步。
在Pandas中,一些函數(shù)意義純粹,但也有一些函數(shù)指的是使用Pandas的方式,以及為什么一種方法比另一種更好。這兒有一些節(jié)省大量的時間和精力Pandas函數(shù)和使用方法,這些效率驚人的神器千萬不要錯過。
itertuples()
確實(shí),它并不是純粹的函數(shù),而是指使用Pandas的更有效方法,是循環(huán)訪問數(shù)據(jù)集的快捷方法。在花時間理解注釋部分之前,可以用更有效的方法計算總列值,在此筆者僅提出一些要點(diǎn)。
下面是一列簡單數(shù)據(jù)集,數(shù)字范圍為1到1百萬。
- df =pd.DataFrame(data={
- 'Number': range(1, 1000000)
- })
這是前幾行的示例:
現(xiàn)在列舉一個錯誤的方式。輸入一個總計變量并將其設(shè)置為0. 然后,通過使用iterrows()循環(huán)訪問數(shù)據(jù)集,并在total的基礎(chǔ)上增加當(dāng)前行的值,與此同時統(tǒng)計操作時間。以下是代碼:
- %%timetotal= 0for _, row in df.iterrows():
- total += row['Number']
- total>>> Wall time: 18.7 s
這項(xiàng)小小的操作歷時將近19秒,而現(xiàn)在有一個更快捷的方法,與上述操作大致相同,但要加iteruples 而不是 iterrows:
- %%timetotal= 0for row in df.itertuples(index=False):
- total += row.Number
- total>>> Wall time: 82.1 ms
筆者沒有計算時間,但可以看到操作速度提高非常明顯。下次執(zhí)行循環(huán)時請記住這一點(diǎn)。
nlargest()和nsmallest()
筆者計算了兩個緯度/經(jīng)度對之間的距離(以公里為單位)。那是第一步操作,第二步是選擇距離最小的前N條記錄。
輸入-nsmallest()。nlargest()將返回N個最大值,而nsmallest()將恰好相反。
看看它的實(shí)際結(jié)果。在實(shí)際操作中,筆者準(zhǔn)備了一個小的數(shù)據(jù)集:
- df =pd.DataFrame(data={
- 'Name': ['Bob', 'Mark', 'Josh','Anna', 'Peter', 'Dexter'],
- 'Points': [37, 91, 66, 42, 99, 81]
- })
結(jié)果如下:
現(xiàn)在該數(shù)據(jù)集不是僅僅6行,而是包含了6000行,為了找到表現(xiàn)最好的學(xué)生,即分?jǐn)?shù)最高,一種方法是這樣的:
- df['Points'].nlargest(3)
但這不是最佳解決方案,它會導(dǎo)致以下結(jié)果,沒有清楚顯示真實(shí)姓名:
改善方法如下:
- df.nlargest(3,columns='Points')
怎么樣,是不是看起來更棒了:
以幾乎相同的操作來找到3個表現(xiàn)最差的學(xué)生-使用nsmallest()功能:
- df.nsmallest(3,columns='Points')
輸出結(jié)果如下:
cut()
這一部分將繼續(xù)使用上一部分中的數(shù)據(jù)集,來回顧一下:
- df =pd.DataFrame(data={
- 'Name': ['Bob', 'Mark', 'Josh','Anna', 'Peter', 'Dexter'],
- 'Points': [37, 91, 66, 42, 99, 81]
- })
cut()函數(shù)的基本原理是將值分為不同的區(qū)間。下面是最簡單的示例,將從Points屬性創(chuàng)建兩個容器:
- pd.cut(df['Points'],bins=2)
現(xiàn)在還看不出效果。但是如何輸入從0到50的區(qū)間,以及第二個從50到100的區(qū)間呢?聽起來有點(diǎn)麻煩。以下為代碼:
- pd.cut(df['Points'],bins=[0, 50, 100])
但是需要注意的是,您要顯示的是Fail而不是(0,50],要顯示Pass而不是(50,100]。你需要這樣做:
- pd.cut(df['Points'],bins=[0, 50, 100], labels=['Fail', 'Pass'])
對于剛?cè)腴T的程序員,這些功能將有助于節(jié)省時間和精力;如果你是資深程序員,本文或許能幫你加強(qiáng)對這些函數(shù)的了解,避免每次都得從頭開始捋,因?yàn)檫@樣毫無意義。