不要使用 apply() 将项目映射到任何输出

Do not map item to any output using apply()

假设我有一个 groupby 对象、一个 DataFrame 或任何其他具有 apply() 方法的对象。我希望某些元素不映射到任何输出。例如,在我的例子中,我有一个 groupby 并且我希望满足特定条件的组被忽略。我怎样才能做到这一点?我在正在应用的函数中尝试了 return None,但输出仍然有该组的条目(它为空但它仍然存在)。

例如,假设一个 DataFrame 如下所示:

good_row            272.0  42440.0  29893408.0
good_row_2          142.0  22360.0  12965953.0
bad_row             171.0  26920.0  14726556.0

我想 运行 df.apply(fn, axis=1) 这样对于好的行,fn returns 一些输出,对于坏的行,fn 告诉应用于 "ignore" 该行,并且输出没有 bad_row 的条目。为了便于演示,我在这里使用了 DataFrame 而不是 groupby,但这是相同的想法。

您可以 return pd.Series(index=['output_column1', 'output_column2', ...]) 而不是 None,然后删除所有 NaN 值的行,如下所示:

cleaned_output_df = output_df.drop_na(axis=0, how='all')

或者,如果您事先知道您不希望将函数应用到哪些行,则可以在使用 apply.

之前将其过滤掉
df.loc[boolean_array].apply(your_function_goes_here)

df.query("column_a > 15").apply(your_function_goes_here)

您还可以使用 groupby 对象的过滤功能过滤对象,请参阅 docs 示例。语法如下所示:

grouped = df.groupby('column_A')
filtered = grouped.filter(some_function_that_takes_a_df_and_returns_a_bool)

首先过滤您的数据框,然后将您的函数应用于过滤后的结果。

假设区分好行和坏行的标准是第二列与第三列的比值小于或等于0.0018。我们还假设您想要对所有单元格(符合条件)中的所有值进行平方。您可以使用以下代码:

import pandas as pd
df = pd.DataFrame(data=[
        {'a': 272., 'b': 42440., 'c': 29893408.},
        {'a': 142., 'b': 22360., 'c': 12965953.},
        {'a': 171., 'b': 26920., 'c': 14726556.}
    ], index=[
        'good_row',
        'good_row_2',
        'bad_row'
    ])

# One line, operator chaining
df[df['b'] / df['c'] <= 0.0018].apply(pow, args=(2,), axis=1)

# Three lines with intermediate objects
good_row_index = df['b'] / df['c'] <= 0.0018
filtered_df = df[good_row_index]
filtered_df.apply(pow, args=(2,), axis=1)