解决这个矩阵的 Pythonic 方法
Pythonic Way to Solve this Matrix
我一直在思考这个问题,但我似乎无法解决这个问题。
我想用三个未知数 x、y、z 的方程求解矩阵,使它们都等于相同的数。
假设我的方程是:
x + 3 = A
y(2y - 2) = 2A
z(4z - 1) = A
所以我可以构造一个如下所示的矩阵:
[(X + 3) , 0 , 0] [0] [A]
[ 0 ,(2y - 2), 0] [y] = [2A]
[ 0 , , 0, (4z -1)] [z] [A]
我知道 numpy has a linear algebra 但那只是在已知答案 (A) 的情况下。
我的问题是,我是否必须构建一个循环来暴力破解 (A) 的答案,或者是否有更 pythonic 的方式来回答这些方程组?
您没有包含 3 个方程和 3 个未知数的系统。您有一个包含 3 个方程和 4 个未知数的系统:x、y、z 和 A。
这意味着你的答案将在 A 上参数化,因为你没有足够的方程来求解所有未知数。
解决一般问题system of polynomial equations can be done by the so-called Groebner basis approach, which is what sympy uses。以下是有关如何使用该库解决此问题或类似问题的片段:
from sympy.solvers.polysys import solve_poly_system
from sympy.abc import x, y, z, A
f1 = x + 3 - A
f2 = y * (2 * y - 2) - 2 * A
f3 = z * (4 * z - 1) - A
solve_poly_system([f1, f2, f3], x, y, z)
# Outputs:
# [(A - 3, -sqrt(4*A + 1)/2 + 1/2, -sqrt(16*A + 1)/8 + 1/8),
# (A - 3, -sqrt(4*A + 1)/2 + 1/2, sqrt(16*A + 1)/8 + 1/8),
# (A - 3, sqrt(4*A + 1)/2 + 1/2, -sqrt(16*A + 1)/8 + 1/8),
# (A - 3, sqrt(4*A + 1)/2 + 1/2, sqrt(16*A + 1)/8 + 1/8)]
如您所见,结果需要固定A
的值才能完全确定。
线性代数只能求解变量的倍数,不能求解幂(这就是为什么它被称为 线性,即直线方程,Ax + By + Cz = 0
).
对于这组方程你可以用二次方程式来求解:
x + 3 = a => x = a - 3
y * (y - 1) = a => y**2 - y - a = 0
y = (1 +/- (1 + 4*a) ** 0.5) / 2
= 0.5 +/- (0.25 + a) ** 0.5
(a >= -0.25 for real roots)
z * (4*z - 1) = a => 4 * z**2 - z - a = 0
z = (1 +/- (1 + 16*a) ** 0.5) / 8
= 0.125 +/- (0.015625 + 0.25*a) ** 0.5
(a >= -0.0625 for real roots)
然后
def solve(a):
assert a >= -0.625, "No real solution"
x = a - 3
yoffs = (0.25 * a) ** 0.5
ylo = 0.5 - yoffs
yhi = 0.5 + yoffs
zoffs = (0.015625 + 0.25 * a) ** 0.5
zlo = 0.125 - zoffs
zhi = 0.125 + zoffs
return [
(x, ylo, zlo),
(x, ylo, zhi),
(x, yhi, zlo),
(x, yhi, zhi)
]
我一直在思考这个问题,但我似乎无法解决这个问题。
我想用三个未知数 x、y、z 的方程求解矩阵,使它们都等于相同的数。
假设我的方程是:
x + 3 = A
y(2y - 2) = 2A
z(4z - 1) = A
所以我可以构造一个如下所示的矩阵:
[(X + 3) , 0 , 0] [0] [A]
[ 0 ,(2y - 2), 0] [y] = [2A]
[ 0 , , 0, (4z -1)] [z] [A]
我知道 numpy has a linear algebra 但那只是在已知答案 (A) 的情况下。
我的问题是,我是否必须构建一个循环来暴力破解 (A) 的答案,或者是否有更 pythonic 的方式来回答这些方程组?
您没有包含 3 个方程和 3 个未知数的系统。您有一个包含 3 个方程和 4 个未知数的系统:x、y、z 和 A。
这意味着你的答案将在 A 上参数化,因为你没有足够的方程来求解所有未知数。
解决一般问题system of polynomial equations can be done by the so-called Groebner basis approach, which is what sympy uses。以下是有关如何使用该库解决此问题或类似问题的片段:
from sympy.solvers.polysys import solve_poly_system
from sympy.abc import x, y, z, A
f1 = x + 3 - A
f2 = y * (2 * y - 2) - 2 * A
f3 = z * (4 * z - 1) - A
solve_poly_system([f1, f2, f3], x, y, z)
# Outputs:
# [(A - 3, -sqrt(4*A + 1)/2 + 1/2, -sqrt(16*A + 1)/8 + 1/8),
# (A - 3, -sqrt(4*A + 1)/2 + 1/2, sqrt(16*A + 1)/8 + 1/8),
# (A - 3, sqrt(4*A + 1)/2 + 1/2, -sqrt(16*A + 1)/8 + 1/8),
# (A - 3, sqrt(4*A + 1)/2 + 1/2, sqrt(16*A + 1)/8 + 1/8)]
如您所见,结果需要固定A
的值才能完全确定。
线性代数只能求解变量的倍数,不能求解幂(这就是为什么它被称为 线性,即直线方程,Ax + By + Cz = 0
).
对于这组方程你可以用二次方程式来求解:
x + 3 = a => x = a - 3
y * (y - 1) = a => y**2 - y - a = 0
y = (1 +/- (1 + 4*a) ** 0.5) / 2
= 0.5 +/- (0.25 + a) ** 0.5
(a >= -0.25 for real roots)
z * (4*z - 1) = a => 4 * z**2 - z - a = 0
z = (1 +/- (1 + 16*a) ** 0.5) / 8
= 0.125 +/- (0.015625 + 0.25*a) ** 0.5
(a >= -0.0625 for real roots)
然后
def solve(a):
assert a >= -0.625, "No real solution"
x = a - 3
yoffs = (0.25 * a) ** 0.5
ylo = 0.5 - yoffs
yhi = 0.5 + yoffs
zoffs = (0.015625 + 0.25 * a) ** 0.5
zlo = 0.125 - zoffs
zhi = 0.125 + zoffs
return [
(x, ylo, zlo),
(x, ylo, zhi),
(x, yhi, zlo),
(x, yhi, zhi)
]