使用Lambda函数在Panda中通过两个现有列创建一个新列

39

我可以通过定义用户函数并使用apply来在Pandas中添加新列。然而,我想使用lambda来实现这一点;有没有什么方法可以绕过这个问题?

例如,df有两列ab。我想创建一个新的列c,它等于ab之间最长的长度。

df = pd.DataFrame({'a':['dfg','f','fff','fgrf','fghj'], 'b' : ['sd','dfg','edr','df','fghjky']})

类似这样的内容:

df['c'] = df.apply(lambda x, len(df['a']) if len(df['a']) > len(df['b']) or len(df['b']) )

一种方法:

df['c'] = df.apply(lambda x: max([len(x) for x in [df['a'], df['b']]]))

这会产生一个由NaN组成的列。

      a       b   c
0   dfg      sd NaN
1     f     dfg NaN
2   fff     edr NaN
3  fgrf      df NaN
4  fghj  fghjky NaN
2个回答

46
你可以使用函数map和通过函数np.where进行选择。更多信息
print df
#     a     b
#0  aaa  rrrr
#1   bb     k
#2  ccc     e
#condition if condition is True then len column a else column b
df['c'] = np.where(df['a'].map(len) > df['b'].map(len), df['a'].map(len), df['b'].map(len))
print df
#     a     b  c
#0  aaa  rrrr  4
#1   bb     k  2
#2  ccc     e  3

下一个解决方案是使用参数axis=1的函数apply

axis = 1 or ‘columns’: 将函数应用于每一行

df['c'] = df.apply(lambda x: max(len(x['a']), len(x['b'])), axis=1)

3
对于未来的读者,错误在于忘记了axis = 1(这导致了KeyError 'a',因为我们正在迭代行索引器[0,1,2,3,4]而不是df ['a'],df [' b ']。此外,Jezraels Solution#2更加简洁,因为lambda已经循环遍历了行。 - Fed

0

在字符串操作方面,要特别注意,因为pandas中的字符串操作未经过优化,因此Python循环实际上可能比向量化的pandas方法表现更好。因此,列表推导是一种可行的方法;它既易读又非常快速:

df['c'] = [max(len(a), len(b)) for a, b in zip(df['a'], df['b'])]

为了让代码更短,您可以尝试使用 applymap():

df['c'] = df.applymap(len).max(1)

如果你正在使用if条件来应用lambda函数,请确保同时提供else部分。
df['c'] = df.apply(lambda row: len(row['a']) if len(row['a']) > len(row['b']) else len(row['b']), axis=1)

一般来说,应该尽可能避免使用lambda表达式,因为pandas有许多优化的操作可以直接作用于列。例如,如果您需要找到每行的最大值,只需调用max(axis=1),如:df[['a', 'b']].max(1)

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接