示例代码:
np.random.seed(0)
df1 = pd.DataFrame(np.random.choice(10, (5, 4)), columns=list('ABCD'))
df2 = pd.DataFrame(np.random.choice(10, (5, 4)), columns=list('ABCD'))
df3 = pd.DataFrame(np.random.choice(10, (5, 4)), columns=list('ABCD'))
df4 = pd.DataFrame(np.random.choice(10, (5, 4)), columns=list('ABCD'))
1、进行算术运算
pd.eval("df1.A + df2.A") # 返回 pd.Series object
pd.eval("abs(df1) ** .5") # 返回 pd.DataFrame object
2、进行比较
pd.eval("df1 > df2")
pd.eval("df1 > 5")
pd.eval("df1 < df2 and df3 < df4")
pd.eval("df1 in [1, 2, 3]")
pd.eval("1 < 2 < 3")
3、复杂运算
pd.eval('df1.A * (df1.index > 1)')
4、解析器选择:parser=...参数
pd.eval
解析表达式字符串以生成语法树时,支持两种不同的解析器选项:pandas
和python
。两者之间的主要区别通过稍有不同的优先级规则突出显示。
使用默认的解析器pandas
,重载位运算符&
和|
它们实现矢量AND
和OR
与pandas对象的操作都会有相同的运算符优先级的and
和or
。
pd.eval("(df1 > df2) & (df3 < df4)")
pd.eval("df1 > df2 & df3 < df4")
# pd.eval("df1 > df2 & df3 < df4", parser='pandas')
pd.eval("df1 > df2 and df3 < df4")
括号是必须的,使用parens覆盖按位运算符的更高优先级:
(df1 > df2) & (df3 < df4)
parser='python'
评估字符串时保持与python实际运算符优先级规则的一致:
pd.eval("(df1 > df2) & (df3 < df4)", parser='python')
5、后端选择:engine=...参数
有两个选项numexpr
(默认)和python
。该numexpr选项使用为性能优化的numexpr
后端。
使用'python'
后端,您对表达式的求值类似于将表达式传递给python的eval函数。您可以灵活地执行更多内部表达式,例如字符串操作。
df = pd.DataFrame({'A': ['abc', 'def', 'abacus']})
pd.eval('df.A.str.contains("ab")', engine='python')
0 True
1 False
2 True
Name: A, dtype: bool
注意:使用'python'
,除非知道自己在做什么,否则通常不建议将此更改此选项。
相关文档:Python pandas.DataFrame.eval函数方法的使用
参考文档:https://stackoverflow.com/questions/53779986/dynamic-expression-evaluation-in-pandas-using-pd-eval