我有任何符号:
In [1]: from sympy import *
In [2]: import numpy as np
In [3]: x=Symbol('x')
我创建了任何矩阵:
In [4]: a=Matrix([[2*x**2,3+x],[4*x**3,-5*x]])
In [5]: a
Out[5]:
Matrix([
[2*x**2, x + 3],
[4*x**3, -5*x]])
如果x=1
我想评估矩阵a
。我使用命令eval
:
In [6]: x=1
In [7]: eval('a')
Out[7]:
Matrix([
[2*x**2, x + 3],
[4*x**3, -5*x]])
我想获得这个输出:
Out[7]:
Matrix([
[2, 4],
[4, -5]])
我在做什么错了?
答案 0 :(得分:0)
使用subs method:
import sympy as sy
x = sy.Symbol('x')
a = sy.Matrix([[2*x**2,3+x],[4*x**3,-5*x]])
print(a.subs(dict(x=1)))
# [2, 4]
# [4, -5]
print(a.evalf(subs=dict(x=1)))
# [2.0, 4.0]
# [4.0, -5.0]
如果要替换多个符号,只需将它们添加到替换词典中即可。例如,
a.subs(dict(x=1, y=exp(5)))
请注意,如果您定义
x = sy.Symbol('x')
然后您绑定名称x
到对象sy.Symbol('x')
。如果您稍后分配
x = 1
然后你重新绑定名称x
到另一个对象int
1.旧的Symbol
对象仍然存在,它只是名称{ {1}}不再引用它。 (在Python名称(又名变量)中只是映射到对象)。
同时,如果您将x
绑定到a
:
Matrix
a = sy.Matrix([[2*x**2,3+x],[4*x**3,-5*x]])
对象可以使用Matrix
为Symbol
的{{1}}。请注意,repr
不是 Python变量,而是x
对象本身。
因此,将x
重新分配给1对Symbol
没有影响。这就是为什么
x
不会将新约束替换为a
。相反,eval('a')
只是在全局命名空间中查找裸名x
,发现它映射到eval('a')
对象并返回a
。
如果您希望Matrix在更改Matrix
时自动更新,一种可能的解决方案是子类Matrix
并定义一个为您执行x
调用的新属性。例如,
Matrix
产量
subs
请注意,您必须使用import sympy as sy
import math
class UpdatingMatrix(sy.Matrix):
def __init__(self, *args):
super(UpdatingMatrix, self).__init__(*args)
self._names = set([symbol.name for expr in self.mat
for symbol in expr.free_symbols])
@property
def val(self):
return self.subs({name:eval(name) for name in self._names})
x = sy.Symbol('x')
y = sy.Symbol('y')
a = UpdatingMatrix([[2*x**2,3+x*y],[4*x**3,-5*x]])
x = 100
y = 1
print(a.val)
来查看更新后的值;在执行[ 20000, 103]
[4000000, -500]
之类的作业时,我没有看到自动更改a.val
的方法。无论如何,这可能都不可取,因为如果可能的话,那么a
无法再次更新自己以后再分配x = 1
(因为a
将不再依赖{ {1}}。)使用上述解决方案,每次访问x = 2
时,都会重新应用替换,因此a
会返回x
相对于当前值的值a.val
和a.val
。