我试图将sympy用作某些转换/数学代码的后端,并遇到了这个问题。
from sympy.parsing.sympy_parser import parse_expr
from sympy.physics import units
type(units.newton) # -> sympy.physics.units.quantities.Quantity
parse_expr('2*Newton').subs({'Newton':units.newton}) # -> 2N
parse_expr('2*newton').subs({'newton':units.newton}) # -> 2N
parse_expr('2*n').subs({'n':units.newton}) # -> 2N
parse_expr('2*N').subs({'N':units.newton}) # -> raises TypeError below
parse_expr('N').subs() # -> raises AttributeError below
parse_expr('N') # -> <function sympy.core.evalf.N(x, n=15, **options)>
TypeError: unsupported operand type(s) for *: 'Integer' and 'function'
AttributeError: 'function' object has no attribute 'subs'
似乎sympy代替了evalf.N函数而不是提供的unit.newton。是否有可以调整的替换顺序,或从替换选项中删除“ N”功能的方法?
编辑:已验证的逃避N
使用的是evalf.N函数,但是要避免是否被使用似乎是一个问题。使用.subs(..., global_dict=...)
尝试过,对错误没有影响。
parse_expr('N') is sympify('N') # -> True
sympify('N') is evalf.N # -> True
答案 0 :(得分:2)
parse_expr
文档中有一个可选参数:
global_dict : dict, optional
A dictionary of global variables. By default, this is initialized with
from sympy import *; provide this parameter to override this behavior
(for instance, to parse "Q & S").
from sympy import *
在全局nampespace中引入了一个函数N
,parse_expr()
在解析最后三个示例中的'N'时正在使用该函数。
您可以在全局名称空间中重新定义'N':
N = units.newton
parse_expr('2*N') -> 2*newton
如果您无法重新定义'N',则制作一个globals()
的副本,修改该副本,然后将其传递给parse_expr()
:
globals_with_units = dict(globals())
globals_with_units['N'] = units.newton
parse_expr('2*N', global_dict=globals_with_units) -> 2*newton
parse_expr()
还带有一个local_dict
参数:
local_dict : dict, optional
A dictionary of local variables to use when parsing.
它可用于覆盖全局名称空间中“ N”的定义。
parse_expr('2*N', local_dict={'N':units.newton}) -> 2*newton