Pandas处理空DataFrame调用apply的最佳实践咨询
问题描述
我在Pandas代码里常用一种模式:创建逐行应用的函数来生成新列,示例代码如下:
def apply_function(row): if row["A"] == "valueA": return "foo" elif row["B"] == "valueB": return "bar" else: return "baz" df["applied_column"] = df.apply(apply_function, axis=1)
当DataFrame不为空时,这段代码能正常运行;但如果df是空的,apply会返回一个DataFrame,导致赋值时抛出异常。
我现在用下面的样板代码处理:
if not df.empty: df["applied_column"] = df.apply(apply_function, axis=1) else: df["applied_column"] = None
但这种写法不够优雅,我想知道这是不是Pandas处理该场景的标准方式,有没有更优的实践方案?
更优实践方案
直接判断空DataFrame的写法不算标准最优解,有几种更简洁优雅且规范的方式:
1. 指定apply的返回类型(推荐)
在apply时通过result_type参数强制返回Series,即使DataFrame为空,也能正常完成赋值:
df["applied_column"] = df.apply(apply_function, axis=1, result_type="reduce")
result_type="reduce"会确保返回一维的Series,空DataFrame下会得到空Series,赋值时不会报错,且列的类型能和非空情况保持一致(不会出现None导致的object类型混乱)。
2. 用assign实现链式操作
如果偏好链式代码风格,可以结合assign和条件判断,写法更紧凑:
import pandas as pd df = df.assign( applied_column=df.apply(apply_function, axis=1) if not df.empty else pd.Series(dtype=str) )
这里指定空Series的类型和非空时的返回类型一致(比如示例中的str),保证列类型统一。
3. 替换apply为矢量化操作(性能最优)
apply逐行处理性能较差,尤其是数据量大的场景,建议用矢量化的numpy.select或者Pandas原生方法替代:
import numpy as np conditions = [ df["A"] == "valueA", df["B"] == "valueB" ] choices = ["foo", "bar"] df["applied_column"] = np.select(conditions, choices, default="baz")
这种方式完全矢量化,空DataFrame下也能直接生成对应类型的空列,没有异常问题,同时性能比apply提升数倍甚至数十倍。
内容的提问来源于stack exchange,提问作者Fernando Jesus Garcia Hipola
相关产品推荐
相关产品推荐

