2017-09-21 2 views
2

B를 (1,0,0) (0, -1,0) (0,0,1)파이썬에서 두 행렬로 방정식을 푸는 방법은 무엇입니까?

시도했을 때 행렬 A는 A*B*A = B*A*B이고 A^2는 1을 찾아야합니다. sympy에 : sympy.solve(A*B*A - B*A*A)

import sympy as sp 
a,b,c,d,e,f,g,h,k = sp.symbols('a b c d e f g h k') 
B = sp.Matrix([[1,0,1],[0,-1,0],[0,0,1]]) 
A = sp.Matrix([[a,b,c],[d,e,f],[g,h,k]]) 
sp.solve([A*B*A - B*A*B,B**2-sp.eye(3)]) 

을하고도 나는 numpy.linalg을 시도했지만이 선형 문제가되지 않습니다 나는 모든의

+1

'sympy'를 사용하면 해당 기호의 기호 및 값이 아닌 값의 답을 얻을 수 있습니다. 따라서 코드의 마지막 줄을'print sp.solve (A * B * A - B * A * A) '로 수정하면 algerbraic 대답을 볼 수 있습니다. 당신이 원하는 것이거나 실제 수치 솔루션을 원하십니까? – DrBwts

+0

나는 약간의 자유가 있음을 안다. 예를 들어, 'g'와 'h'를 사용하여 답변을 원합니다. – Nikita

+0

미안하지만 분명하지 않습니다.기호에 대한 대답을 원하면 코드가 작동합니다. – DrBwts

답변

2

먼저, linalg이 도움이되지 않습니다 어떤 결과가 없습니다 : 알 수없는 A 자체가 곱해진다. 9 개의 미지수가있는 18 개의 2 차 방정식 시스템을 풀고 싶습니다. 일반 시스템의 경우 솔루션은 없지만 여기에는 많은 구조가 있습니다.

내 버전의 SymPy (1.1.1)에서 행렬 방정식 A*B*A=B*A*B 또는 A*A=I 중 하나라도 직접적으로 풀려는 시도는 적당한 시간 내에 끝나지 않습니다. 그래서 saintsfan342000의 조언을 따르고 최소화 문제로서 수치 적으로 문제에 접근 해 봅시다. 이것은 내가 그것을 어떻게 있습니다 :

import numpy as np 
from scipy.optimize import minimize  
B = np.array([[1,0,0], [0,-1,0], [0,0,1]]) 
def func(A, B): 
    A = A.reshape((3, 3)) 
    return np.linalg.norm(A.dot(B).dot(A)-B.dot(A).dot(B))**2 + np.linalg.norm(A.dot(A)-np.eye(3))**2 
while True: 
    guess = np.random.uniform(-2, 2, size=(9,)) 
    res = minimize(func, guess, args=(B,)) 
    if res.fun < 1e-15: 
     A = res.x.reshape((3, 3)) 
     print(A) 

최소화 할 수있는 기능이 A*B*A-B*A*BA*A-I의 Frobenius의 규범의 제곱의 합이다. minimize이 걸릴 일부 로컬 미니 마가 있기 때문에 루프에 최소화를 넣었습니다. 그래서 발견 된 최소값이 0에 충분히 가깝지 않을 때, 나는 결과를 무시하고 다시 시작합니다. 잠시 동안 실행 한 후, 스크립트는

[[ 0.70386835 0.86117949 -1.40305355] 
[ 0.17193376 0.49999999 0.81461157] 
[-0.25409118 0.73892171 -0.20386834]] 

같은 행렬의 무리를 인쇄 할 모든 주 두 가지 중요한 기능 :

  • 중앙 요소 A가 [1,1] 1/2
  • 입니다
  • 행렬 (대각선 요소의 합)의 흔적은 1입니다.

SymPy가 시스템을 해결하는 데 도움이되도록이 정보를 사용 합니다. 나는 여전히 두 방정식을 던지기를 원하지 않는다. 그래서 나는 한 번에 하나씩 방정식을 얻으려고 노력한다.

from sympy import * 
var('a:h')     # a quick way to declare a bunch of symbols 
B = Matrix([[1, 0, 0], [0, -1, 0], [0, 0, 1]]) 
A = Matrix([[a, b, c], [d, S(1)/2, f], [g, h, S(1)/2-a]]) # S(1)/2 is a way to get rational 1/2 instead of decimal 0.5 
print(solve(A*B*A - B*A*B)) 
print(solve(A*A - eye(3))) 

지금 solve 성공 다음과 같은 인쇄 :

[{b: h*(4*f*h - 3)/(2*g), d: -g/(2*h), a: 2*f*h - 1/2, c: -f*h*(4*f*h - 3)/g}] 
[{b: h*(4*f*h - 3)/(2*g), d: -g/(2*h), a: 2*f*h - 1/2, c: -f*h*(4*f*h - 3)/g}] 

우와! 수치 적으로 발견 된 두 가지 제약 조건을 통해 두 행렬 방정식은 동일합니다! 나는 그것을 기대하지 않았다. 따라서 우리는 이미 솔루션을 가지고 있습니다 :

A = Matrix([[2*f*h - S(1)/2, h*(4*f*h - 3)/(2*g), -f*h*(4*f*h - 3)/g], [-g/(2*h), S(1)/2, f], [g, h, 1 - 2*f*h]]) 

(임의의 f, g, h).


참고 : A = B는 A [1,1] = 1/2의 요구 사항에서 위에 제외 된 간단한 해결 방법입니다. 나는 이것이 의도라고 상상한다. 대칭 그룹 S의 3 차원 적 표현을 충실히 찾고있는 것으로 보입니다. S .

관련 문제