簡體   English   中英

Python Pandas:在具有相同索引的多行中檢查列的值

[英]Python Pandas: Check the value of a column over multiple rows with the same index

我有一個非常復雜的(對我來說)情況,我需要處理一個 dataframe ,每個索引都有多行,這可能是三種場景之一,具體取決於某個列的值。

dataframe 看起來像這樣:

Index   Account Postfix ID  val1    val2
AA11    AA      11      aa  1       2
AA11    AA      11      aa  1       2
AA11    AA      11      aa  1       2
BB22    BB      22      bb  1       1
BB22    BB      22      NA  2       2
BB22    BB      22      NA  3       3
CC33    CC      33      NA  1       2
CC33    CC      33      NA  1       2
CC33    CC      33      NA  1       2

每個唯一索引都可以屬於以下三種情況之一:

  • A: 總是填充 ID,從每個索引的第一行獲取 val1 和 val2
  • S:有時會填充 ID,從 ID != Na 的行中獲取 val1,從 ID = Na 的行中獲取 val2
  • N:從不填充 ID,對所有行求和 val1 和 val2

我的第一個問題是我無法弄清楚如何檢查同一索引的多行中列的值。

我在想類似的事情:

indices = df.index.unique()
for index in indices:
    df[ScenarioA] = np.all(df.loc[index, ID])
    df[ScenarioN] = np.all(np.logical_not(df.loc[index, ID]))
    df[ScenarioS] = np.logical_and(np.logical_not(df[ScenarioA]),np.logical_not(df[ScenarioN]))

但這會導致所有行都被標記為 ScenarioN,而實際上結果應該如下所示:

Index   Account Postfix ID  val1    val2  ScenarioA ScenarioS ScenarioN
AA11    AA      11      aa  1       2     True      False     False
AA11    AA      11      aa  1       2     True      False     False
AA11    AA      11      aa  1       2     True      False     False
BB22    BB      22      bb  1       1     False     True      False
BB22    BB      22      NA  2       2     False     True      False
BB22    BB      22      NA  3       3     False     True      False
CC33    CC      33      NA  1       2     False     False     True
CC33    CC      33      NA  1       2     False     False     True
CC33    CC      33      NA  1       2     False     False     True

一旦我完成了,我需要執行總和並最終得到類似下面的結果,但我認為這部分不會太難,因為我可以通過 Scenario go 並根據需要執行計算:

Index   Account Postfix ID  val1    val2
AA11    AA      11      aa  1       2
BB22    BB      22      bb  1       5
CC33    CC      33      NA  3       6

在我嘗試將 T/F 分配給 Scenario 列的部分中,我做錯了什么?

不確定這是否是你 r 之后的結果,希望它可以指導你解決你的具體挑戰:

grouping = df.groupby('Index').ID

#create some anonymous functions
#determine groups that completely have no null
#those that have some null
#those that have nulls all through
alls = lambda x: x.isna().all()
anys = lambda x: x.isna().any()
notnull = lambda x: x.notna().all()
all_null = grouping.apply(alls)
any_null = grouping.apply(anys)
all_not_null = grouping.apply(notnull)

#get the individual groups
full = all_not_null.index[all_not_null.array]
empty = all_null.index[all_null.array]
partially_empty = any_null.index[any_null.array].difference(empty)

#get the different dataframes for each group
step1 = df.loc[df.Index.isin(full)].groupby('Index').first()


#some nulls
cond1 = df.Index.isin(partially_empty) & (df.ID.notna())
cond2 = df.Index.isin(partially_empty) &(df.ID.isna())

step2 = df.loc[cond1]
step2 = step2.assign(val2 = df.loc[cond2,'val2'].sum())

#nulls all the way
step3 = df.loc[df.Index.isin(empty)]
temp = step3.groupby(['Index']).agg({'val1':'sum','val2':'sum'})

step3 = step3.drop_duplicates('Index')
step3 = step3.assign(val1 = temp['val1'].squeeze(), val2 = temp['val2'].squeeze())

#combine the three dataframes
pd.concat([step1.reset_index(),step2,step3],ignore_index=True)

    Index   Account Postfix ID  val1    val2
0   AA11      AA      11    aa    1      2
1   BB22      BB      22    bb    1      5
2   CC33      CC      33    NaN   3      6

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM