これは信じられないほど単純でばかげた質問のように思えますが、私が見つけたものはすべて複雑すぎて理解できませんでした.
次の 2 つの非常に基本的な連立方程式があります。
X = 2x + 2z
Y = z - x
X と Y の両方を知っているとすると、x と z を見つけるにはどうすればよいでしょうか? 手動で行うのは非常に簡単ですが、コードでこれを行う方法がわかりません。
これは信じられないほど単純でばかげた質問のようです
全くない。これは非常に良い質問ですが、残念ながら複雑な答えになっています。解こう
a * x + b * y = u
c * x + d * y = v
ここでは 2x2 のケースに固執します。より複雑なケースでは、ライブラリを使用する必要があります。
最初に注意すべきことは、Cramer 式は使いにくいということです。行列式を計算すると
a * d - b * c
あなたが持っているとすぐにa * d ~ b * c
、壊滅的なキャンセルがあります。これは典型的なケースであり、警戒する必要があります。
シンプルさと安定性の最適なトレードオフは、部分ピボットです。と仮定し|a| > |c|
ます。次に、システムは次と同等です
a * c/a * x + bc/a * y = uc/a
c * x + d * y = v
これは
cx + bc/a * y = uc/a
cx + dy = v
そして今、最初のものから2番目のものを引くと
cx + bc/a * y = uc/a
(d - bc/a) * y = v - uc/a
これで簡単に解決できます:y = (v - uc/a) / (d - bc/a)
とx = (uc/a - bc/a * y) / c
. 最大数で除算するため、計算d - bc/a
は よりも安定ad - bc
しています (あまり明白ではありませんが、成り立ちます。非常に近い係数で計算を行います。なぜそれが機能するかがわかります)。
の場合|c| > |a|
は、行を入れ替えて同様に進めます。
コード内 (Python 構文を確認してください):
def solve(a, b, c, d, u, v):
if abs(a) > abs(c):
f = u * c / a
g = b * c / a
y = (v - f) / (d - g)
return ((f - g * y) / c, y)
else
f = v * a / c
g = d * a / c
x = (u - f) / (b - g)
return (x, (f - g * x) / a)
完全なピボットを使用できます (最初の除算が常に最大の係数になるように x と y を交換する必要があります) が、これは書くのが面倒で、2x2 の場合はほとんど必要ありません。
nxn の場合、すべてのピボット処理はLU 分解にカプセル化されるため、ライブラリを使用する必要があります。
sove するアルゴリズム: Ax + By = C, Dx + Ey = F
始める
1) PRINT "Enter A"
2) INPUT A
3) PRINT "Enter B"
4) INPUT B
5) PRINT "Enter C"
6) INPUT C
7) PRINT "Enter D"
8) INPUT D
9) PRINT "Enter E"
10) INPUT E
11) PRINT "Enter F"
21) INPUT F
22) detS <-- AE - BC
22) detX <-- CE - BF
24) detY <-- AF - CD
25) x <-- detX / detS
26) y <-- detY / detS
27) PRINT x, y
終わり