SymPy:将字符串解析为流形上的函数

2024-04-29 13:02:05 发布

您现在位置:Python中文网/ 问答频道 /正文

我试图用SymPy和SymPy的diffgeom包来定义流形上的一个方程。因为这个等式是由用户输入的,所以它以字符串的形式发送到程序中,因此在代码中定义流形之前定义它。为了执行有意义的计算,我尝试用流形上定义的符号替换“联化”符号。在

这是一个由用户提供的函数。在

H = sympify('m*a - f')

流形的坐标也由用户以字符串形式提供。在

^{pr2}$

之后的一切都是自动化的。在

from sympy.diffgeom import Manifold, Patch, CoordSystem
from sympy import sympify, Symbol
# Standard manifold definitions
M = Manifold(name='Temp', dim=2)
P = Patch('P', M)
R = CoordSystem('R', P, ['a','f'])
coords = R.coord_functions()
Dx = R.base_vectors()

print(H.diff(a)) # Returns 'm' as expected
print(Differential(H)(Dx[0])) # Returns '0' as expected

第一次替换效果很好。我可以使用Differential()获得预期的导数。在

H = H.subs(a,coords[0])

print(H.diff(a)) # Returns '0' as expected
print(Differential(H)(Dx[0])) # Returns 'm' as expected
print(Differential(H)(Dx[1])) # Returns '0' as expected

第二个替代是事情变得奇怪。由于新坐标是在流形上定义的,而不是标准符号,因此().diff()命令工作正常并返回0,但我不能再使用Differential()获取导数。在

H = H.subs(f,coords[1])

print(H.diff(f)) # Returns '0' as expected
print(Differential(H)(Dx[0])) # Crashes code
print(Differential(H)(Dx[1])) # Also crashes code

看起来diffgeom正在尝试执行一个转换来计算导数,但是实际上不应该进行任何转换,因为这都是在同一个坐标系中。我是不是从根本上遗漏了什么?或者有没有更简单的方法把字符串解析为流形上的表达式?在

这里是抛出的完整错误。我真的不能从中得到什么,除了SymPy试图在我不期望的情况下转换坐标。在

Traceback (most recent call last):
  File "/Users/msparapa/Documents/Python/gprops/examples/test.py", line 37, in <module>
    print(Differential(H)(Dx[0])) # Crashes code
  File "/Users/msparapa/anaconda/lib/python3.5/site-packages/sympy/diffgeom/diffgeom.py", line 765, in __call__
    return vector_fields[0].rcall(self._form_field)
  File "/Users/msparapa/anaconda/lib/python3.5/site-packages/sympy/core/basic.py", line 538, in rcall
    return Basic._recursive_call(self, args)
  File "/Users/msparapa/anaconda/lib/python3.5/site-packages/sympy/core/basic.py", line 552, in _recursive_call
    return expr_to_call(*on_args)
  File "/Users/msparapa/anaconda/lib/python3.5/site-packages/sympy/diffgeom/diffgeom.py", line 592, in __call__
    jac = self._coord_sys.jacobian(b._coord_sys, coords)
  File "/Users/msparapa/anaconda/lib/python3.5/site-packages/sympy/diffgeom/diffgeom.py", line 277, in jacobian
    to_sys, self._dummies).jacobian(self._dummies)
  File "/Users/msparapa/anaconda/lib/python3.5/site-packages/sympy/diffgeom/diffgeom.py", line 270, in coord_tuple_transform_to
    transf = self.transforms[to_sys]
KeyError: CoordSystem(R, Patch(P, Manifold(Temp, 2)), (a, f))

Tags: inpyasline流形usersreturnsfile
1条回答
网友
1楼 · 发布于 2024-04-29 13:02:05

经过进一步调查,原因是有相同名称的符号。解决方法是本质上使用here描述的方法进行替换,或者完全使用不同的命名约定。在

为了执行替换,我需要一次交换所有变量。这是用下面的代码块完成的。在

set = dict(zip([a,f],coords))
H = H.subs(set, simultaneous=True)

其中“a”和“f”是基本符号,“coords”是流形上的符号列表。替代不是同时进行的,而是顺序进行的,例如

^{pr2}$

抛出同样的错误。我相信这是因为两个都被埋藏在流形坐标中。在这里我们可以看到这个输出。在

BaseScalarField(CoordSystem(Symbol('R'), Patch(Symbol('P'), Manifold(Symbol('M'), Integer(2))), Tuple(Symbol('f'), Symbol('a'))), Integer(0))

符号('f')和符号('a')都显示在坐标系下。这里发生的是,当我在表达式中替换第二个变量f时,SymPy正在查看流形变量a,并看到一个同名的变量。因此,它不仅试图替换基本符号f,而且还试图替换埋藏在坐标系定义中的符号f,然后可能会促使坐标系转换。在

相关问题 更多 >