[英]Get n smallest values of a subset of a dataframe in Python
我正在嘗試做一些類似於在 Geeks for Geeks 工作的例子。
在該示例中,他們處理了 dataframe 的 NBA(籃球)球員,並找到了聯盟中最小的 5 名球員(按身高或體重)。
所有這些都是有道理的,我能夠輕松地將它應用到我正在使用的數據集,直到我想做一些更精確的數據切片。 例如,我想找出每支 NBA 球隊中體型最小的 3 名球員。
我希望數據 output 如下所示:
團隊 | 播放器 | 重量 | 其他數據 x | 其他數據 |
---|---|---|---|---|
A隊 | 玩家 1 | 最小的 | xxxxxx | yyyyyy |
A隊 | 玩家 2 | 第二小 | xxxxxx | yyyyyy |
A隊 | 玩家 3 | 第三小 | xxxxxx | yyyyyy |
---------- | ---------- | ---------- | -------------- | -------------- |
B隊 | 玩家 1 | 最小的 | xxxxxx | yyyyyy |
B隊 | 玩家 2 | 第二小 | xxxxxx | yyyyyy |
B隊 | 玩家 3 | 第三小 | xxxxxx | yyyyyy |
---------- | ---------- | ---------- | -------------- | -------------- |
團隊 C | 玩家 1 | 最小的 | xxxxxx | yyyyyy |
團隊 C | 玩家 2 | 第二小 | xxxxxx | yyyyyy |
團隊 C | 玩家 3 | 第三小 | xxxxxx | yyyyyy |
---------- | ---------- | ---------- | -------------- | -------------- |
我已經嘗試按照我想要的方式進行以下兩項工作。
df2 = df1.groupby('Team').nsmallest(3, ['Weight'])
df2 = df1.groupby('Team')['Weight'].nsmallest(3)
關於如何進行多次數據切割的任何建議? 我還想保留所有其他列中的數據,而不是球隊/球員/體重數據。
您可以利用df.groupby('Team')["Weight"].nsmallest(3)
已經在該結果的index
列中為您提供所需的索引這一事實。 所以你可以只使用iloc
原始 dataframe 中的那些索引。
import pandas as pd
# making data frame
df = pd.read_csv("https://media.geeksforgeeks.org/wp-content/uploads/nba.csv")
new_df = df.iloc[df.groupby('Team')["Weight"].nsmallest(3).index.get_level_values(1)]
結果:
>>> new_df.head(5)
Name Team Number ... Weight College Salary
318 Dennis Schroder Atlanta Hawks 17.0 ... 172.0 NaN 1763400.0
323 Jeff Teague Atlanta Hawks 0.0 ... 186.0 Wake Forest 8000000.0
311 Kirk Hinrich Atlanta Hawks 12.0 ... 190.0 Kansas 2854940.0
0 Avery Bradley Boston Celtics 0.0 ... 180.0 Texas 7730337.0
3 R.J. Hunter Boston Celtics 28.0 ... 185.0 Georgia State 1148640.0
[5 rows x 9 columns]
然后您可以將Team
和Name
設置為多索引:
>>> new_df.set_index(["Team", "Name"]).head(6)
Number Position ... College Salary
Team Name ...
Atlanta Hawks Dennis Schroder 17.0 PG ... NaN 1763400.0
Jeff Teague 0.0 PG ... Wake Forest 8000000.0
Kirk Hinrich 12.0 SG ... Kansas 2854940.0
Boston Celtics Avery Bradley 0.0 PG ... Texas 7730337.0
R.J. Hunter 28.0 SG ... Georgia State 1148640.0
Isaiah Thomas 4.0 PG ... Washington 6912869.0
[6 rows x 7 columns]
Groupby Team
,在Weight
上應用 pd.Series.nsmallest ,將級別降低到 1,將其轉換為 frame,然后將其內部合並回Team
和Weight
上的實際 dataframe
df.groupby('Team')['Weight'].apply(lambda row: row.nsmallest(3)).to_frame('Weight').droplevel(1).merge(df, on=['Team', 'Weight'], how='inner')
Team Weight Name Number Position Age Height College Salary
0 Boston Celtics 180.0 Avery Bradley 0.0 PG 25.0 6-2 Texas 7730337.0
1 Boston Celtics 185.0 R.J. Hunter 28.0 SG 22.0 6-5 Georgia State 1148640.0
2 Boston Celtics 190.0 Terry Rozier 12.0 PG 22.0 6-2 Louisville 1824360.0
PS:在添加預期 output 時,從原始數據創建樣本,人們可能會對這種捏造的預期 output 感到困惑,這與實際數據完全不同。
import pandas as pd
details = {
'Team' : ['A', 'A', 'A', 'A', 'B', 'B', 'B','B'],
'Age' : [23, 21, 22, 19,18,17,20,22],
}
# creating a Dataframe object
df = pd.DataFrame(details)
df=df.sort_values(by=['Team','Age'])
df['tmp']=1
df['seq']=df.groupby('Team')['tmp'].cumsum()
#filter out based on Nth basis on seq column
#filter code here
print(df.head())
稍后您可以根據“最小”字連接到 seq 列並刪除 tmp 列。
如果你這樣做
df2 = df1.groupby('Team').apply(lambda x: x.nsmallest(3, ['Weight'])
你會得到一個由數據幀組成的可迭代對象,每個數據幀都有一個團隊中最小的三個。 然后,您可以將它們 append 放在一起或將它們放在一個多索引 dataframe 中。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.