如何在自定义函数中访问 Pandas 系列值

How to access Pandas series value in a custom function

我正在开展一个项目,根据他们的 GPS 数据监控我的 running/jogging 活动的 5k 时间。我目前正在 Jupyter 笔记本中探索我的数据,现在意识到我需要排除一些活动。

每个 activity 是数据框中的一行。虽然我确实想排除一些行,但我不想将它们从我的数据框中删除,因为我还将使用 df 进行其他计算。

我在 df 中添加了一列以及一个自定义函数,用于检查一行的无效原因。 运行 可能由于多种原因被排除。

In []:
    # add invalidity reasons column & update logic
    df['invalidity_reasons'] = ''
    
    def maintain_invalidity_reasons(reason):
        """logic for maintaining ['invalidity reasons']"""
        reasons = []
        if invalidity_reasons == '':
            return list(reason)
        else:
            reasons = invalidity_reasons
            reasons.append(reason)
            return reasons

我过滤到 df 中的特定行并将它们传递给我的函数。下面的示例 returns 来自 df 的一组五行。下面是在我的 Jupyter notebook 中使用该函数的示例。

In []:
    columns = ['distance','duration','notes']
    
    filt = (df['duration'] < pd.Timedelta('5 minutes'))
    df.loc[filt,columns].apply(maintain_invalidity_reasons('short_run'),axis=1)

Out []:
    ---------------------------------------------------------------------------
    NameError                                 Traceback (most recent call last)
    <ipython-input-107-0bd06407ef08> in <module>
          2 
          3 filt = (df['duration'] < pd.Timedelta('5 minutes'))
    ----> 4 df.loc[filt,columns].apply(maintain_invalidity_reasons(reason='short_run'),axis=1)
    
    <ipython-input-106-60264b9c7b13> in maintain_invalidity_reasons(reason)
          5     """logic for maintaining ['invalidity reasons']"""
          6     reasons = []
    ----> 7     if invalidity_reasons == '':
          8         return list(reason)
          9     else:
    
    NameError: name 'invalidity_reasons' is not defined

这是我的过滤器输出的示例,如果我删除了对我的函数的 .apply() 调用

In []:
columns = ['distance','duration', 'notes','invalidity_reasons']

filt = (df['duration'] < pd.Timedelta('5 minutes'))
df.loc[filt,columns]

Out []:

看来我的问题在于不知道如何指定我要引用特定行的 'invalidity_reasons' index/column(不确定正确的术语)中的标量值。

我尝试使用以下变体调整 IF 语句。我还尝试将函数 with/out 应用于轴参数。我卡住了,请帮忙!

if 'invalidity_reasons' == '':
if s['invalidity_reasons'] == '':

这几乎是盲目的尝试,但希望对您有所帮助。在下文中,我使用这个简单的框架作为示例(有一些东西可以使用):

df = pd.DataFrame({'Col': range(5)})

现在如果你定义

def maintain_invalidity_reasons(current_reasons, new_reason):
    if current_reasons == '':
        return [new_reason]
    if type(current_reasons) == list:
        return current_reasons + [new_reason]
    return [current_reasons] + [new_reason]

将另一列 invalidity_reasons 添加到 df

df['invalidity_reasons'] = ''

填充一个单元格(为了举例)

df.loc[0, 'invalidity_reasons'] = 'a reason'
   Col invalidity_reasons
0    0           a reason
1    1                   
2    2                   
3    3                   
4    4                   

构建过滤器

filt = (df.Col < 3)

然后

df.loc[filt, 'invalidity_reasons'] = (df.loc[filt, 'invalidity_reasons']
                                        .apply(maintain_invalidity_reasons,
                                               args=('another reason',)))

你会得到

   Col          invalidity_reasons
0    0  [a reason, another reason]
1    1            [another reason]
2    2            [another reason]
3    3                            
4    4                            

这是否与您正在寻找的内容相似?