36

方程式があるとしましょう:

2x + 6 = 12

代数でそれを見ることができますx = 3。を解くことができるプログラムをPythonで作成するにはどうすればよいxですか? 私はプログラミングが初めてで、andを見ましたeval()exec()、自分がやりたいことをさせる方法がわかりません。私は外部ライブラリ (SAGE など) を使用したくありません。単純な Python でこれを実行したいと考えています。

4

5 に答える 5

40

SymPyはどうですか?彼らのソルバーは、あなたが必要としているもののように見えます。ライブラリを自分で構築したい場合は、ソース コードを参照してください。</p>

于 2012-05-08T13:54:09.427 に答える
28

この問題にアプローチするには、数値的方法と記号的方法の 2 つの方法があります。

数値的に解決するには、最初に「実行可能な」関数としてエンコードする必要があります-値を入れて、値を取得します。例えば、

def my_function(x):
    return 2*x + 6

文字列を解析して、そのような関数を自動的に作成することは十分に可能です。2x + 6リストに解析するとします[6, 2](リストのインデックスは x のべき乗に対応するため、6*x^0 + 2*x^1)。それで:

def makePoly(arr):
    def fn(x):
        return sum(c*x**p for p,c in enumerate(arr))
    return fn

my_func = makePoly([6, 2])
my_func(3)    # returns 12

次に、関数に x 値を繰り返し挿入し、結果と見つけたいものの違いを調べ、その x 値を微調整して (できれば) 違いを最小限に抑える別の関数が必要です。

def dx(fn, x, delta=0.001):
    return (fn(x+delta) - fn(x))/delta

def solve(fn, value, x=0.5, maxtries=1000, maxerr=0.00001):
    for tries in xrange(maxtries):
        err = fn(x) - value
        if abs(err) < maxerr:
            return x
        slope = dx(fn, x)
        x -= err/slope
    raise ValueError('no solution found')

ここには多くの潜在的な問題があります - 関数が実際に解を持っていると仮定して (つまり、x^2 + 2 = 0 に対する実数値の答えがない)、適切な開始 x 値を見つけること、計算精度の限界に達すること、など。しかし、この場合、エラー最小化関数が適切であり、良い結果が得られます。

solve(my_func, 16)    # returns (x =) 5.000000000000496

この解決策は絶対的ではなく、正確に正しいというわけではないことに注意してください。完璧にする必要がある場合、または連立方程式を解析的に解いてみたい場合は、より複雑な獣、つまりシンボリック ソルバーに目を向ける必要があります。

Mathematica や Maple のようなシンボリック ソルバーは、代数や微積分などに関する多くの組み込みルール (「知識」) を備えたエキスパート システムです。それは、sin の導関数が cos であること、kx^p の導関数が kpx^(p-1) であることなどを「認識」しています。方程式を与えると、現在の場所 (方程式) から目的の場所 (可能な限り単純な方程式の形式、できれば解決策) までの一連のルール適用であるパスを見つけようとします。 .

あなたの例の方程式は非常に単純です。シンボリック ソリューションは次のようになります。

=> LHS([6, 2]) RHS([16])

# rule: pull all coefficients into LHS
LHS, RHS = [lh-rh for lh,rh in izip_longest(LHS, RHS, 0)], [0]

=> LHS([-10,2]) RHS([0])

# rule: solve first-degree poly
if RHS==[0] and len(LHS)==2:
    LHS, RHS = [0,1], [-LHS[0]/LHS[1]]

=> LHS([0,1]) RHS([5])

あなたの解があります:x = 5.

これがアイデアの趣を与えることを願っています。実装の詳細 (優れた完全なルール セットを見つけ、各ルールをいつ適用するかを決定する) には、何年もの労力がかかります。

于 2012-05-08T18:23:00.977 に答える
12

Python は良いかもしれませんが、神ではありません...

方程式を解く方法はいくつかあります。分析ソリューションを探している場合は、SymPy について既に言及されています。

数値解だけでよければ、Numpy には役立つルーチンがいくつかあります。多項式の解だけに興味がある場合は、numpy.roots が機能します。具体的には、あなたが言及した場合:

>>> import numpy
>>> numpy.roots([2,-6])
array([3.0])

より複雑な式については、scipy.fsolve を参照してください。

いずれにせよ、ライブラリを使用して脱出することはできません。

于 2012-05-08T14:01:14.290 に答える
6

正の整数の非常に限られた一連の方程式のみを解きたい場合は、次のようにします。mx + c = ym, c, y

import re
def solve_linear_equation ( equ ):
    """
    Given an input string of the format "3x+2=6", solves for x.
    The format must be as shown - no whitespace, no decimal numbers,
    no negative numbers.
    """
    match = re.match(r"(\d+)x\+(\d+)=(\d+)", equ)
    m, c, y = match.groups()
    m, c, y = float(m), float(c), float(y) # Convert from strings to numbers
    x = (y-c)/m
    print ("x = %f" % x)

いくつかのテスト:

>>> solve_linear_equation("2x+4=12")
x = 4.000000
>>> solve_linear_equation("123x+456=789")
x = 2.707317
>>> 

のような任意の方程式を認識して解きたい場合は、 、、MATLABや Symbolic Toolbox などsin(x) + e^(i*pi*x) = 1に似た、ある種のシンボリック数学エンジンを実装する必要があります。maximaMathematicasolve()

于 2012-05-08T14:10:06.827 に答える
2

別のツールを使用してください。Wolfram AlphaMapleROctaveMatlabまたはその他の代数ソフトウェア パッケージのようなもの。

初心者として、このような重要な問題を解決しようとするべきではありません。

于 2012-05-08T13:57:05.620 に答える