在mathematica中创建符号正交矩阵

发布于 2024-12-20 03:24:22 字数 55 浏览 2 评论 0原文

我需要在 Mathematica 中创建一个 3 x 3 实正交符号矩阵。 我怎样才能这样做呢?

I need to create a 3 by 3 real orthonormal symbolic matrix in Mathematica.
How can I do so?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(5

思念满溢 2024-12-27 03:24:22

并不是我推荐这个,但是......

m = Array[a, {3, 3}];
{q, r} = QRDecomposition[m];
q2 = Simplify[q /. Conjugate -> Identity]

所以 q2 是一个符号正交矩阵(假设我们处理实数)。

Not that I recommend this, but...

m = Array[a, {3, 3}];
{q, r} = QRDecomposition[m];
q2 = Simplify[q /. Conjugate -> Identity]

So q2 is a symbolic orthogonal matrix (assuming we work over reals).

宣告ˉ结束 2024-12-27 03:24:22

我认为您似乎想要在 Mathematica 中进行一些 SO(3) 组参数化。您将只有 3 个独立的符号(变量),因为矢量相互正交有 6 个约束,并且范数等于 1。一种方法是围绕 3 个轴构建独立旋转,并将这些矩阵相乘。下面是执行此操作的代码(可能太复杂):

makeOrthogonalMatrix[p_Symbol, q_Symbol, t_Symbol] :=
  Module[{permute, matrixGeneratingFunctions},
    permute =  Function[perm, Permute[Transpose[Permute[#, perm]], perm] &];
    matrixGeneratingFunctions = 
       Function /@ FoldList[
            permute[#2][#1] &,
            {{Cos[#], 0, Sin[#]}, {0, 1, 0}, {-Sin[#], 0, Cos[#]}},
            {{2, 1, 3}, {3, 2, 1}}];
    #1.#2.#3 & @@  MapThread[Compose, {matrixGeneratingFunctions, {p, q, t}}]];

这是其工作原理:

In[62]:= makeOrthogonalMatrix[x,y,z]
Out[62]= 
{{Cos[x] Cos[z]+Sin[x] Sin[y] Sin[z],Cos[z] Sin[x] Sin[y]-Cos[x] Sin[z],Cos[y] Sin[x]},
 {Cos[y] Sin[z],Cos[y] Cos[z],-Sin[y]},
 {-Cos[z] Sin[x]+Cos[x] Sin[y] Sin[z],Cos[x] Cos[z] Sin[y]+Sin[x] Sin[z],Cos[x] Cos[y]}}

您可以通过对各个列(或行)点积使用 Simplify 来检查矩阵是否正交。

You seem to want some SO(3) group parametrization in Mathematica I think. You will only have 3 independent symbols (variables), since you have 6 constraints from mutual orthogonality of vectors and the norms equal to 1. One way is to construct independent rotations around the 3 axes, and multiply those matrices. Here is the (perhaps too complex) code to do that:

makeOrthogonalMatrix[p_Symbol, q_Symbol, t_Symbol] :=
  Module[{permute, matrixGeneratingFunctions},
    permute =  Function[perm, Permute[Transpose[Permute[#, perm]], perm] &];
    matrixGeneratingFunctions = 
       Function /@ FoldList[
            permute[#2][#1] &,
            {{Cos[#], 0, Sin[#]}, {0, 1, 0}, {-Sin[#], 0, Cos[#]}},
            {{2, 1, 3}, {3, 2, 1}}];
    #1.#2.#3 & @@  MapThread[Compose, {matrixGeneratingFunctions, {p, q, t}}]];

Here is how this works:

In[62]:= makeOrthogonalMatrix[x,y,z]
Out[62]= 
{{Cos[x] Cos[z]+Sin[x] Sin[y] Sin[z],Cos[z] Sin[x] Sin[y]-Cos[x] Sin[z],Cos[y] Sin[x]},
 {Cos[y] Sin[z],Cos[y] Cos[z],-Sin[y]},
 {-Cos[z] Sin[x]+Cos[x] Sin[y] Sin[z],Cos[x] Cos[z] Sin[y]+Sin[x] Sin[z],Cos[x] Cos[y]}}

You can check that the matrix is orthonormal, by using Simplify over the various column (or row) dot products.

酷到爆炸 2024-12-27 03:24:22

我找到了一种“直接”的方式来强加特殊的正交性。
见下文。

(*DEFINITION OF ORTHOGONALITY AND SELF ADJUNCTNESS CONDITIONS:*) 
MinorMatrix[m_List?MatrixQ] := Map[Reverse, Minors[m], {0, 1}] 
CofactorMatrix[m_List?MatrixQ] := MapIndexed[#1 (-1)^(Plus @@ #2) &, MinorMatrix[m], {2}] 
UpperTriangle[ m_List?MatrixQ] := {m[[1, 1 ;; 3]], {0, m[[2,   2]], m[[2, 3]]}, {0, 0, m[[3, 3]]}}; 
FlatUpperTriangle[m_List?MatrixQ] := Flatten[{m[[1, 1 ;; 3]], m[[2, 2 ;; 3]], m[[3, 3]]}];
Orthogonalityconditions[m_List?MatrixQ] := Thread[FlatUpperTriangle[m.Transpose[m]] == FlatUpperTriangle[IdentityMatrix[3]]]; 
Selfadjunctconditions[m_List?MatrixQ] := Thread[FlatUpperTriangle[CofactorMatrix[m]] == FlatUpperTriangle[Transpose[m]]]; 
SO3conditions[m_List?MatrixQ] := Flatten[{Selfadjunctconditions[m], Orthogonalityconditions[m]}]; 

(*Building of an SO(3) matrix*) 
mat = Table[Subscript[m, i, j], {i, 3}, {j, 3}]; 
$Assumptions = SO3conditions[mat]

然后

Simplify[Det[mat]] 

给出 1;...并

MatrixForm[Simplify[mat.Transpose[mat]]

给出单位矩阵;
...最终

MatrixForm[Simplify[CofactorMatrix[mat] - Transpose[mat]]]

给出一个零矩阵。

=================================================== ======================

这就是我问问题时正在寻找的!
不过,请让我知道您对此方法的想法。

马塞勒斯

I have found a "direct" way to impose special orthogonality.
See below.

(*DEFINITION OF ORTHOGONALITY AND SELF ADJUNCTNESS CONDITIONS:*) 
MinorMatrix[m_List?MatrixQ] := Map[Reverse, Minors[m], {0, 1}] 
CofactorMatrix[m_List?MatrixQ] := MapIndexed[#1 (-1)^(Plus @@ #2) &, MinorMatrix[m], {2}] 
UpperTriangle[ m_List?MatrixQ] := {m[[1, 1 ;; 3]], {0, m[[2,   2]], m[[2, 3]]}, {0, 0, m[[3, 3]]}}; 
FlatUpperTriangle[m_List?MatrixQ] := Flatten[{m[[1, 1 ;; 3]], m[[2, 2 ;; 3]], m[[3, 3]]}];
Orthogonalityconditions[m_List?MatrixQ] := Thread[FlatUpperTriangle[m.Transpose[m]] == FlatUpperTriangle[IdentityMatrix[3]]]; 
Selfadjunctconditions[m_List?MatrixQ] := Thread[FlatUpperTriangle[CofactorMatrix[m]] == FlatUpperTriangle[Transpose[m]]]; 
SO3conditions[m_List?MatrixQ] := Flatten[{Selfadjunctconditions[m], Orthogonalityconditions[m]}]; 

(*Building of an SO(3) matrix*) 
mat = Table[Subscript[m, i, j], {i, 3}, {j, 3}]; 
$Assumptions = SO3conditions[mat]

Then

Simplify[Det[mat]] 

gives 1;...and

MatrixForm[Simplify[mat.Transpose[mat]]

gives the identity matrix;
...finally

MatrixForm[Simplify[CofactorMatrix[mat] - Transpose[mat]]]

gives a Zero matrix.

========================================================================

This is what I was looking for when I asked my question!
However, let me know your thought on this method.

Marcellus

紫轩蝶泪 2024-12-27 03:24:22

Marcellus,您必须使用 SO(3) 的一些参数化,因为您的通用矩阵必须反映 < strong>RP3组拓扑。如果没有多值性或奇异点,任何单一参数化都无法覆盖整个组。维基百科有一个关于 SO(3) 上的各种图表的精彩页面。

也许概念上最简单的之一是李代数的指数映射 so(3)。
定义一个反对称的实 A(跨越 so(3)),

A = {{0, a, -c},
     {-a, 0, b},
     {c, -b, 0}};

MatrixExp[A]SO(3) 的一个元素。
我们可以检查是否如此,使用

Transpose[MatrixExp[A]].MatrixExp[A] == IdentityMatrix[3] // Simplify

如果我们写t^2 = a^2 + b^2 + c^2,我们可以将矩阵指数简化为

{{   b^2 + (a^2 + c^2) Cos[t]  , b c (1 - Cos[t]) + a t Sin[t], a b (1 - Cos[t]) - c t Sin[t]}, 
 {b c (1 - Cos[t]) - a t Sin[t],    c^2 + (a^2 + b^2) Cos[t]  , a c (1 - Cos[t]) + b t Sin[t]}, 
 {a b (1 - Cos[t]) + c t Sin[t], a c (1 - Cos[t]) - b t Sin[t],    a^2 + (b^2 + c^2) Cos[t]}} / t^2

注意,这基本上是相同的参数化为 RotationMatrix 给出。
与输出进行比较

RotationMatrix[s, {b, c, a}] // ComplexExpand // Simplify[#, Trig -> False] &;
% /. a^2 + b^2 + c^2 -> 1

Marcellus, you have to use some parametrization of SO(3), since your general matrix has to reflect the RP3 topology of the group. No single parametrization will cover the whole group without either multivaluedness or singular points. Wikipedia has a nice page about the various charts on SO(3).

Maybe one of the conceptually simplest is the exponential map from the Lie algebra so(3).
Define an antisymmetric, real A (which spans so(3))

A = {{0, a, -c},
     {-a, 0, b},
     {c, -b, 0}};

Then MatrixExp[A] is an element of SO(3).
We can check that this is so, using

Transpose[MatrixExp[A]].MatrixExp[A] == IdentityMatrix[3] // Simplify

If we write t^2 = a^2 + b^2 + c^2, we can simplify the matrix exponential down to

{{   b^2 + (a^2 + c^2) Cos[t]  , b c (1 - Cos[t]) + a t Sin[t], a b (1 - Cos[t]) - c t Sin[t]}, 
 {b c (1 - Cos[t]) - a t Sin[t],    c^2 + (a^2 + b^2) Cos[t]  , a c (1 - Cos[t]) + b t Sin[t]}, 
 {a b (1 - Cos[t]) + c t Sin[t], a c (1 - Cos[t]) - b t Sin[t],    a^2 + (b^2 + c^2) Cos[t]}} / t^2

Note that this is basically the same parametrization as RotationMatrix gives.
Compare with the output from

RotationMatrix[s, {b, c, a}] // ComplexExpand // Simplify[#, Trig -> False] &;
% /. a^2 + b^2 + c^2 -> 1
萌能量女王 2024-12-27 03:24:22

虽然我真的很喜欢马塞勒斯对自己问题的回答,但这并不完全正确。不幸的是,他所达到的条件也导致

Simplify[Transpose[mat] - mat]

评估为零矩阵!这显然是不对的。这里有一个既正确又更直接的方法:

OrthogonalityConditions[m_List?MatrixQ] := Thread[Flatten[m.Transpose[m]] == Flatten[IdentityMatrix[3]]];
SO3Conditions[m_List?MatrixQ] := Flatten[{OrthogonalityConditions[m], Det[m] == 1}];

即将旋转矩阵乘以其转置结果得到单位矩阵,并且旋转矩阵的行列式是1。

Although I really like the idea of Marcellus' answer to his own question, it's not completely correct. Unfortunately, the conditions he arrives at also result in

Simplify[Transpose[mat] - mat]

evaluating to a zero matrix! This is clearly not right. Here's an approach that's both correct and more direct:

OrthogonalityConditions[m_List?MatrixQ] := Thread[Flatten[m.Transpose[m]] == Flatten[IdentityMatrix[3]]];
SO3Conditions[m_List?MatrixQ] := Flatten[{OrthogonalityConditions[m], Det[m] == 1}];

i.e. multiplying a rotation matrix by its transpose results in the identity matrix, and the determinant of a rotation matrix is 1.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文