簡體   English   中英

將 function 應用於 pandas dataframe (lambda) 中的所有行

[英]Apply function to all rows in pandas dataframe (lambda)

我有以下 function 用於獲取行的最后一個非零值的列名

import pandas as pd

def myfunc(X, Y):
    df = X.iloc[Y]
    counter = len(df)-1
    while counter >= 0:
        if df[counter] == 0:
            counter -= 1
        else:
            break
    return(X.columns[counter])

使用以下代碼示例

data = {'id':  ['1', '2', '3', '4', '5', '6'],
        'name': ['AAA', 'BBB', 'CCC', 'DDD', 'EEE', 'GGG'],
        'A1': [1, 1, 1, 0, 1, 1],
        'B1': [0, 0, 1, 0, 0, 1],
        'C1': [1, 0, 1, 1, 0, 0],
        'A2': [1, 0, 1, 0, 1, 0]}

df = pd.DataFrame(data)
df

myfunc(df, 5) # 'B1'

我想知道如何將此 function 應用於 dataframe 中的所有行,並將結果放入df的新列中

我正在考慮遍歷所有行(這可能不是好方法)或將 lambdas 與 apply function 一起使用。 但是,我沒有成功采用最后一種方法。 有什么幫助嗎?

我已經稍微修改了您的 function 以跨行工作:

def myfunc(row):
     counter = len(row)-1
     while counter >= 0:
         if row[counter] == 0:
             counter -= 1
         else:
             break
     return row.index[counter]

現在只需調用df.apply你的 function 和axis=1來為 dataframe 的每一行調用 function:

>>> df.apply(myfunc, axis=1)
0    A2
1    A1
2    A2
3    C1
4    A2
5    B1
dtype: object

但是,您可以放棄自定義 function 並使用此代碼以更快、更簡潔的方式完成您正在尋找的事情:

>>> df[df.columns[2:]].T.cumsum().idxmax()
0    A2
1    A1
2    A2
3    C1
4    A2
5    B1
dtype: object

這是使用DataFrame.idxmax的更簡單和更快的解決方案。

>>> res = df.iloc[:, :1:-1].idxmax(axis=1)
>>> res

0    A2
1    A1
2    A2
3    C1
4    A2
5    B1
dtype: object

這個想法是 select 僅AiBi列並顛倒它們的順序( df.iloc[:, :1:-1] ),然后返回第一次出現最大值的列 label (在這種情況下為 1)每行( .idxmax(axis=1) )。

請注意,此解決方案(作為另一個答案)假定每一行至少包含一個高於零的條目。

如果我們首先屏蔽非零條目(使用.ne(0) ),則可以將此假設放松為“每一行至少包含一個非零條目”。 這是因為.ne(0)產生一個 boolean 掩碼和True > False <=> 1 > 0

>>> res = df.iloc[:, :1:-1].ne(0).idxmax(axis=1)
res

0    A2
1    A1
2    A2
3    C1
4    A2
5    B1
dtype: object

暫無
暫無

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

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