对python apply()
pandas.DataFrame
方法的输出有疑问
为什么当pandas.DataFrame
函数返回pandas.DataFrame
时,此函数会返回与输入(apply
)格式相同1>的<{1}} 与输入相同的形状?
例如
array
代码将返回:
foo = pd.DataFrame([[1,2],[3,4]],columns=['a','b'])
foo.apply(lambda x: [np.min(x)/2,np.max(x)/2], axis='index')
出于某种原因,我想输出一个 a b
0 min(a)/2 min(b)/2
1 max(a)/2 max(b)/2
数组:
pandaq.Series
我试过0 [min(a)/2, max(a)/2]
1 [min(b)/2, max(b)/2]
...
但没有成功。
然后,我该怎么办?
提前谢谢。
答案 0 :(得分:1)
由于结果数组的ndim是2,如果你看到apply
here的主代码,如果ndim为2则应用DataFrame构造函数。
#Main Code
...
# TODO: mixed type case
if result.ndim == 2:
return DataFrame(result, index=self.index, columns=self.columns)
else:
return Series(result, index=self._get_agg_axis(axis))
如果您希望结果为系列,那么请使用类似tuple
而不是列表的内容,即
foo = pd.DataFrame([[1,2],[3,4]],columns=['a','b'])
foo.apply(lambda x: tuple([np.min(x)/2,np.max(x)/2]), axis=1)
输出:
0 (0.5, 1.0)
1 (1.5, 2.0)
dtype: object
希望它有所帮助。
答案 1 :(得分:1)
我更愿意避免apply
可能numpy
操作。
在这种情况下,至少有几种选择。以下是基准测试的示例。如您所见,移动到numpy
越近,结果就越好。
import pandas as pd, numpy as np
foo = pd.DataFrame([[1,2],[3,4]],columns=['a','b'])
foo = pd.concat([foo]*10000, ignore_index=True)
def dark(df):
return df.apply(lambda x: tuple([np.min(x)/2,np.max(x)/2]), axis=1)
def jp1(df):
return [tuple([np.min(x)/2,np.max(x)/2]) for x in foo[['a', 'b']].values]
def jp2(df):
arr = foo[['a', 'b']].values
return list(zip(*(np.min(arr, axis=1)/2, np.max(arr, axis=1)/2)))
%timeit dark(foo) # 4.95s
%timeit jp1(foo) # 298ms
%timeit jp2(foo) # 4.68ms
当然,dark()
会返回pd.Series
,但pandas
会让您通过列表进行分配。