2012-02-29 110 views
15

我正在编写一个函数来解决任意数量的联立方程。等式的数量由函数的其中一个参数设置,每个等式都由多个符号构成 - 与等式一样多的符号。这意味着我不能简单地对方程进行硬编码,甚至不需要将方程组合在一起所需的符号;该功能需要能够处理任意数量的等式。所以,我的问题是,我如何产生一个符号列表?SymPy - 任意数量的符号

我有一个可能的解决方案,但我的直觉告诉我,它不会非常有效。请让我知道是否有更好的方法来做到这一点。

我是新来的SymPy,我仍然感觉我的方式。就我所见,符号需要用一个字符串来定义。因此,我可以通过在字母上添加递增数字(例如't0','t1'等)来产生一系列字符串,将它们添加到列表中,然后使用这些字符串作为参数来创建符号。这些符号本身将存储在一个列表中,并将用于生成方程。

def solveEquations(numEquations): 
    symbolNameList = [] 
    symbolList = [] 
    equationList = [] 
    for i in range(numEquations): 
     name = 't' + str(i) 
     symbolNameList.append(name) 
     symbolList.append(Symbol(name)) 

    for i in range(numEquations): 
     equation = 0 
     for sym in symbolList: 
      equation += sym ** i # Or whatever structure the equation needs 
     equationList.append(equation) 


    #Then go on to solve the equations... 

这是做这件事的最好方法,还是有更高效的方法?

回答

24

symbols功能可用于方便地生成的符号列表

In [1]: symbols('a0:3') 
Out[1]: (a₀, a₁, a₂) 

In [2]: numEquations = 15 

In [3]: symbols('a0:%d'%numEquations) 
Out[3]: (a₀, a₁, a₂, a₃, a₄, a₅, a₆, a₇, a₈, a₉, a₁₀, a₁₁, a₁₂, a₁₃, a₁₄) 
+1

谢谢!这看起来很简单。 – thornate 2012-02-29 07:22:47

+1

它也适用于字母:'符号('a:g')'。 – asmeurer 2012-12-28 10:06:13

+2

只是在这里注意,在sympy这是一个元组,而不是一个列表...主要是一个不能定义的东西列表中的元素:a0 = t + 1会给出错误。 – user836925 2014-01-31 16:50:24

1

您的方法很好,但不需要单独存储符号名称(您可以通过其name属性访问符号名称)。

此外,您还可以表达符号创建多一点简洁(虽然没有更有效的),例如:

symbolList = map(lambda i: Symbol('t' + str(i)), xrange(numEquations)) 

然而,对于你的使用情况(临时变量),虚拟变量可能的方式去:

symbolList = map(Dummy, xrange(numEquations)) 

这是不是真的任何更有效,因为内部的Dummy类也使用一个计数器来生成唯一的名称,但它是一个有点更干净,更清晰。

1

你可以做的dict自动返回一个子类Symbols

import sympy as sym 

class SymDict(dict): 
    # http://stackoverflow.com/a/3405143/190597 
    def __missing__(self, key): 
     self[key]=sym.Symbol(key) 
     return self[key] 

def solveEquations(numEquations): 
    symbol = SymDict() 
    symbolList = ['t'+str(i) for i in range(numEquations)] 
    equationList = [sum(symbol[s]**i for s in symbolList) 
        for i in range(numEquations)] 
    print(equationList) 

solveEquations(3)  
# [3, t0 + t1 + t2, t0**2 + t1**2 + t2**2] 
7

numbered_symbols("t")将返回生成t0发电机,t1t2等。您可以使用start参数来选择不同的起始v ALUE。如果您想使用虚拟变量,请使用numbered_symbols("t", cls=Dummy)

1

随着locals()和字典的理解,你可以反复生成符号和python局部变量具有相似的名称。例如:

>>> symbols_dict = dict(('a%d'%k, symbols('a%d'%k)) for k in range(3)) 
>>> locals().update(symbols_dict) 

检查它的工作原理:

>>> print(expand((a0+a2)*(a0+a1**2))) 
a0**2 + a0*a1**2 + a0*a2 + a1**2*a2