【问题标题】:Why does pandas.DataFrame.apply produces Series instead of DataFrame为什么 pandas.DataFrame.apply 产生 Series 而不是 DataFrame
【发布时间】:2021-10-28 14:57:46
【问题描述】:

我不太明白为什么从下面的代码中 pandas 返回的是 Series 而不是 DataFrame。

import pandas as pd
df = pd.DataFrame([[4,9]]*3, columns = ["A", "B"])

def plus_2(x):
    y =[]
    for i in range(0, len(x)):
        y.append(x[i]+2)
    return y

df_row = df.apply(plus_2, axis = 1) # Applied to each row
df_row

如果我更改 axis=0,它会按预期生成 DataFrame:

import pandas as pd
df = pd.DataFrame([[4,9]]*3, columns = ["A", "B"])

def plus_2(x):
    y =[]
    for i in range(0, len(x)):
        y.append(x[i]+2)
    return y

df_row = df.apply(plus_2, axis = 0) # Applied to each row
df_row

这是输出:

【问题讨论】:

    标签: pandas dataframe apply series


    【解决方案1】:

    在您放置 axis=1 的第一个示例中,您在行级别实现。 这意味着对于每一行 plus_2 函数返回 y 这是两个元素的列表(但列表作为一个整体是单个元素,所以这是 pd.Series)。 根据您的示例,它将返回 3x 列表(每个 2 个元素)。如果是单行,这里是单个列表。

    您可以通过在应用中添加 result_type="expand" 来扩展此结果并创建两列(列表中的每个元素都是新列):

    df_row = df.apply(lambda x: plus_2(x), axis=1, result_type="expand")
    
    # output
    
        0   1
    0   6   11
    1   6   11
    2   6   11
    

    在第二种方法中,您将 axis=0 应用于列级别。 这意味着对于每一列 plus_2 函数返回 y,因此 plus_2 应用了两次,分别用于 A 列和 B 列。这就是它返回数据框的原因:您的输入是包含 A 和 B 列的 DataFrame,每列应用 plus_2 函数并返回 A 和 B 列作为应用 plus_2 函数的结果。

    根据您的示例,它将返回 2x 列表(每个 3 个元素)。这里单个列表是单个列。

    所以axis=1和axis=0的主要区别在于:

    如果您在行级别应用 apply 将返回:

    [6, 11]
    [6, 11]
    [6, 11]
    

    如果您在列级别应用 apply 将返回:

    [6, 6, 6]
    [11, 11, 11]
    

    【讨论】: