maxima による行列計算超入門
足立健朗

Contents
1. 基本的な操作
1.1. 行列の入力
1.2. 行列に名前をつける
1.3. 名前のついた行列に別名をつける (エイリアスをつくる)
1.4. 行列のコピーを作る
1.5. 行列の足し算
1.6. 行列のかけ算
1.7. 行列のスカラー倍
1.8. 行列の冪乗
1.9. 行列の転置
1.10. 階段行列
1.11. 行列の階数
1.12. 逆行列
1.13. 行列式
2. 少しだけ発展した操作
2.1. 行列の行を操作する
2.2. 行列の列を操作する
2.3. 行列の成分の操作
2.4. 連立一次方程式の係数行列
2.5. 連立一次方程式を解く
3. もっと高度な機能について

Date: 2005/10/5.
1222233344555667789910122

足立健朗

1. 基本的な操作
1.1. 行列の入力. まずは、maxima に行列を入力しないといけません。行列を入力するには、関数 matrixを使います。具体例で見てみましょう。
(%i1) matrix([1,2,3],[4,5,6],[7,8,9]);
1 2 3(%o1)  4 5 6 
7 8 9(%i2) µmatrix([a,b,c,d],[e,f,g,h]);¶a b c d(%o2)
e f g h関数 matrix の引数には、入力したい行列の成分を行ごとに”[“と “]“ でくくって、第 1 行から順に並べたものを使います。

1.2. 行列に名前をつける. さて、matrix だけを使っても色々な行列の計算を maxima にさせることは可能なのですが、計算のたびに一々成分を入力するのでは全く疲れてしまいます。そこで、一度入力した行列に適当な名前を付けて、名前で色々な操作ができれば便利です。maxima で、何かの対象に名前を付けるは記号 : を使います。例を見てみましょう。
(%i3) A : matrix([1,2,3],[4,5,6],[7,8,9]);
1 2 3(%o3)  4 5 6 
7 8 9(%i4) µ
B : matrix([a,b,c,d],[e,f,g,h]);¶a b c d(%o4)
e f g h
これで、A, B といった名前で行列を使うことができるようになりました。この A や B を変数と言います。
本当に A、B に入力した行列のデータが入っているか確認しましょう。

(%i5) A;1(%o5)  47(%i6) µB;a(%o6)
e25836 9bfcgdh¶

1.3. 名前のついた行列に別名をつける (エイリアスをつくる). 上の操作で名前 A を与えた行列に、さらに別の名前を付けることもできます。A に別名 A1 を付けるときには(%i7) A1 : A;
1 2 3(%o7)  4 5 6 
7 8 9(%i8) A1;
1 2 3(%o8)  4 5 6 
7 8 9とします。ここで注意することは、A と A1 は実体は同じものなので、後で説明する行列の操作で A の成分を変えてしまうと A1 の成分も同じように変わってしまうと言うことです。逆に、A1 の成分を変えるとA の成分も同じように変わります。

maxima による行列計算超入門

3

1.4. 行列のコピーを作る. それでは、行列の操作をしたいのだが、もとの行列のデータも残して置きたい
ときにはどうすればよいのでしょうか？そのような場合には、行列のコピーを作って使えばいいのです。そうすれば、もとの行列のデータは保存されます。A という行列と同じ成分をもつ、新たな変数 C (つまり Aのコピー) を作るには、maxima の関数 copymatrix と記号 : を使って次の様にします。
(%i9) C :copymatrix(A);
1 2 3(%o9)  4 5 6 
7 8 9(%i10) C;
1 2 3(%o10)  4 5 6 
7 8 9
これで、A と同じ成分を持つ行列 C が得られましたが、今度は A の成分を変化させても C の成分には影響がありませんし、逆もまたしかりです。

1.5. 行列の足し算. 次に、maxima に行列の演算をさせる方法を見ていきましょう。まずは、同じ型の行列の足し算をします。これには、演算子 + を使います。ここで、上で使った行列の名前 A, B, A1, C とその内容の関係をキャンセルして、もう一度、A, B などを定義しなおすことにします。そのために、maximaの命令 kill を使います。
(%i11) kill(A, B, A1, C);(%o11) DONE
これで、準備ができました。足し算の例を見て見ましょう。

(%i12) µ
A : matrix([1,2],[3,4]);¶1 2(%o12)
3 4(%i13) µ
B : matrix([a,b],[c,d]);¶a b(%o13)
c d(%i14) µ
C : A + B;
¶a+1 b+2(%o14)
c+3 d+4
この例では、A と B という 2 × 2-行列を与えて、A + B を計算し、その結果に C という名前を付けています。結果に名前を付ける必要がなければ、単に(%i15) µ
A + B;
a+1(%o15)
c+3b+2d+4¶としても結構です。

1.6. 行列のかけ算. 次に行列と行列のかけ算をしてみましょう。線形代数学で学んだように、行列の積では行列の型が重要ですが、ここではそれについては触れません。行列の積を計算するには、演算子 . を使います。早速、例を見てみましょう。
(%i16) µ
A . B;¶
2c + a 2d + b(%o16)
4c + 3a 4d + 3b(%i17) µ
D : matrix([a,b,c],[d,e,f]);¶a b c(%o17)
d e f4足立健朗(%i18) E : matrix([p,q],[r,s],[t,u]);p q(%o18)  r s t u(%i19) µ
F : D . E;
¶ct + br + ap cu + bs + aq(%o19)
f t + er + dp f u + es + dq
この例では、まず上で定義した２つの 2 × 2-行列 A, B の積 AB を計算しています。次に、2 × 3-行列 D と3 × 2-行列 E を定義してそれらの積 DE を計算し、それに名前 F を付けています。
積が定義できないような行列の組み合わせを入力すると、次のようなエラーメッセージがでます。

(%i20) D . A;
incompatible dimensions - cannot multiply-- an error. Quitting. To debug this try DEBUGMODE(TRUE);

1.7. 行列のスカラー倍. 行列のスカラー倍を計算するには、演算子 * を使います。ここで、例を見る前に今まで使った変数 (名前）をすべてキャンセルしましょう。そのための命令は kill(ALL) です。
(%i21) kill(ALL);(%o0) DONE
それでは、例を始めます。

(%i1) µA : matrix([a,b,c],[d,e,f]);¶a b c(%o1)
d e f(%i2) µB : 3 * A; ¶3a 3b 3c(%o2)
3d 3e 3f1.8. 行列の冪乗. ある行列 A が正方行列ならば、A の冪乗を考えることができます。maxima で正方行列の冪乗を計算するには、演算子 ˆˆ を使います。例を見ましょう。
(%i3) kill(ALL);(%o0) DONE(%i1) A : matrix([2,3,4],[-1,0,3],[2,1,-2]);
2 3 4(%o1)  −1 0 3 
2 1 −2(%i2) A^^3;
26 36 48
36 (%o2)  −12 224 12 −22
この例では A3 を計算しています。本当に正しいかどうか、先ほど扱った行列の積を使って確認してみましょう。

(%i3) A . A . A;
26 36 48
36 (%o3)  −12 224 12 −22

maxima による行列計算超入門

5

確かに正しいようです。冪乗は使うのに注意が必要です。成分が文字式だったり、冪乗の指数が大きかった
りすると計算時間や画面表示が大変な事になるかもしれません。使う前に、他に良い方法 (例えば対角化など) がないかどうか考えて見る方が良いでしょう。

1.9. 行列の転置. ここからは、行列に関する操作とか、行列に関係した諸量の計算のうち、maxima で関数が用意されているものの中で基本的なものを取り上げていくことにしましょう。まずは、行列の転置から始めます。maxima で行列の転置を求めるには、関数 transpose を使います。
(%i4) A;

2 3 4(%o4)  −1 0 3 
2 1 −2(%i5) transpose(A);
2 −1 21 (%o5)  3 0
4 3 −2(%i6) µC : matrix([a,b,c],[d,e,f]);¶a b c(%o6)
d e f(%i7) transpose(C);
a d(%o7)  b e c f
1.10. 階段行列. 与えられた行列 A に対して、それに対し行基本変形を施すことによって得られる階段行列を求めるには、maxima の関数 echelon を使います。ただし、階段行列の定義はテキストごとに少し違うかも知れませんので注意が必要です。
(%i8) kill(ALL);(%o0) DONE(%i1) A : matrix([1,2,3],[4,5,6],[7,8,9]);
1 2 3(%o1)  4 5 6 
7 8 9(%i2) echelon(A);
1 2 3(%o2)  0 1 2 0 0 0(%i3) 
B : matrix([1,2,3],[4,5,6],[7,8,0]);
1 2 3(%o3)  4 5 6 
7 8 0(%i4) C : echelon(B);
1 87 0(%o4)  0 1 14 0 0 1
しかし、maxima で求めた階段行列からテキストの定義に沿った階段行列を求めるのは容易でしょう。

1.11. 行列の階数. 与えられた行列 A に対して、対応する階段行列 echelon(A) の階段の数を、A の階数(rank) と言いましたが、maxima では直接階数を求める関数 rank が用意されています。
(%i5) rank(A);(%o5) 2(%i6) rank(B);6足立健朗(%o6) 3
ここでは、上の行列 A, B の階数を求めています。

1.12. 逆行列. 与えられた n 次正方行列 A の階数が n ならば、A は逆行列 A−1 をもつのですが、maximaで逆行列を求めるには、関数 invert を用います。
(%i7) invert(B);8− 169914− 79(%o7)  92− 199− 1929− 19

しかし、階数が次数より小さいとき、正則でない行列に対して invert を適用すると次のようなエラーメッセージがでます。

(%i8) invert(A);Division by 0-- an error. Quitting.

To debug this try DEBUGMODE(TRUE);

これを避けるには、事前に rank を使って考えている正方行列が正則であるかどうか調べておいた方が良いでしょう。
正則行列を求めるには、別の方法もあります。すでに説明した行列の冪乗を使って、例えば Aˆˆ(-1) のようにすれば、A の逆行列が求まります。

(%i9) B^^(-1);
8− 169914− 79(%o9)  92− 199− 1929− 19

1.13. 行列式. 与えられた正方行列 A の行列式を求めるには、maxima の関数 determinant を使います。
(%i10) determinant(A);(%o10) 0(%i11) determinant(B);(%o11) 27(%i12) determinant(B^^(-1));1(%o12) 27maxima による行列計算超入門

72. 少しだけ発展した操作
2.1. 行列の行を操作する. 与えられた行列から、ある行だけ取り出す、例えば第 i 行を取り出すには、A[i]とタイプするか、または maxima の関数 row を使って、row(A,i) とタイプします。
(%i13) kill(ALL);(%o0) DONE(%i1) A : matrix([a,b,c],[d,e,f],[g,h,i]);a b c(%o1)  d e f g h i(%i2) A[1];(%o2) [a, b, c](%i3) A[2];(%o3) [d, e, f ](%i4) A[3];(%o4) [g, h, i](%i5) ¡row(A,1);¢a b c(%o5)(%i6) ¡row(A,2); ¢d e f(%o6)(%i7) ¡row(A,3);¢g h i(%o7)
2 通りの操作 A[i] と row(A,i) によって得られる結果は似ていますが微妙に意味が異なります。例えば、上の例で A[1] の値である [a,b,c] というのは、a, b, c を並べて得られるリストと呼ばれる型を持ちます。一方、row(A,1) の値である (a b c) は 1 × 3-行列の型を持ちます。
ここで、行列の行基本変形を扱ってみましょう。例えば、A の第 2 行を 2 倍したいときには次のようにします。
(%i8) A[2] : 2 * A[2];(%o8) [2d, 2e, 2f ](%i9) A;abc(%o9)  2d 2e 2f g hi
確かに A の第 2 行が 2 倍されていることがわかりますね。A 自身を変えたくないときには、A のコピーに対して変形操作を適用すればよいでしょう。一方、row の方は上のような方法では使えません。A をもとに戻すつもりで、row(A,2) : (1/2) * row(A,2) とタイプしても、次のようなエラーメッセージを受けとるだけです。

(%i10) row(A,2) : (1/2) * row(A,2);
Improper value assignment:
ROW (A, 2) FALSEfalse-- an error. Quitting. To debug this try DEBUGMODE(TRUE);
もとに戻すには(%i11) A[2] : (1/2) * A[2];(%o11) [d, e, f ](%i12) A;

8

足立健朗


a b c
(%o12)  d e f g h iとします。つぎに、A の第 1 行に第 2 行の 3 倍を加えてみましょう。そのためには、次のようにします。

(%i13) A[1] : A[1] + 3 * A[2];(%o13) [3d + a, 3e + b, 3f + c](%i14) A;
3d + a 3e + b 3f + cdef(%o14) ghi
もとに戻すには、(%i15) A[1] : A[1] - 3 * A[2];(%o15) [a, b, c](%i16) A;
a b c(%o16)  d e f g h iとします。今度は、A の第 1 行と第３行を入れ換えてみます。この操作は、1 度ではできないので、リスト型のダミーの変数 B を使って、次のようにします。

(%i17) B : A[1];(%o17) [a, b, c](%i18) A[1] : A[3];(%o18) [g, h, i](%i19) A[3] : B;(%o19) [a, b, c](%i20) A;g h i(%o20)  d e f a b c2.2. 行列の列を操作する. 与えられた行列から、ある行を取り出すには、例えば行列 A の第 i 行を取り出すには、transpose(transpose(A)[i]) または col(A[i]) とタイプします。
(%i21) kill(ALL);(%o0) DONE(%i1) A : matrix([r,s,t],[u,v,w],[x,y,z]);r s t(%o1)  u v w x y z(%i2) transpose(transpose(A)[1]);r(%o2)  u x(%i3) col(A,1);
r(%o3)  u xmaxima による行列計算超入門

9

ここで、行の操作の所での話しと違い、transpose(transpose(A)[1]) と col(A,1) はともに 3 × 1-行列の型を持ちます。列ベクトルの基本変形も行ベクトルの操作と transpose を組み合わせることで実現可能なのですが、少しややこしくなりますので、ここでは割愛させていただきます。

2.3. 行列の成分の操作. 与えられた行列 A の第 (i,j)-成分を取り出すには、A[i][j] とか、A[i,j] とタイプします。
(%i4) kill(ALL);(%o0) DONE(%i1) A : matrix([1,2,3,4],[5,6,7,8],[9,10,11,12]);
1 2 348 (%o1)  5 6 7
9 10 11 12(%i2) A[2][3];(%o2) 7(%i3) A[2,3];(%o3) 7
この例では、A の第 (2,3) 成分を取り出しています。逆に、A の第 (2,3) 成分に新しい値、例えば x を入れるにはどうしたらいいでしょうか? それには、A[2][3] : x とタイプすれば OK です。

(%i4) A[2,3] : x;(%o4) x(%i5) A;

1 2 34(%o5)  5 6 x 8 
9 10 11 12
今度は、A の第 (3,2)-成分を y に変えてみましょう。A[3,2] : y とタイプして下さい。

(%i6) A[3,2] : y;(%o6) y(%i7) A;
1 2 3 4(%o7)  5 6 x 8 
9 y 11 12
この方法でもうまく行くことがわかりました。

2.4. 連立一次方程式の係数行列. maxima では、連立一次方程式を扱うこともできます。例えば、次の連立一次方程式
= 4,x + 2y + 3z5x + 6y + 7z= 8,
9x + 10y + 11z = 0
を maxima に認識させて、eq1 と言う名前をつけるには、(%i8) kill(ALL);(%o0) DONE(%i1) eq1 : [x+2*y+3*z=4, 5*x+6*y+7*z=8, 9*x+10*y+11*z=12];(%o1) [3z + 2y + x = 4, 7z + 6y + 5x = 8, 11z + 10y + 9x = 12]のように、方程式のリストとして入力します。ここで、eq1 の未知数 (x,y,z) に関する係数行列 A を取り出して見ます。係数行列を求める maxima の関数は、coefmatrix です。これは、次の例の様にして使いま10

足立健朗

す。

(%i2) xx : [x,y,z];(%o2) [x, y, z](%i3) A : coefmatrix(eq1,xx);
1 2 3(%o3)  5 6 7 
9 10 11
ここで xx は [x,y,z] のことです。直接(%i3) A : coefmatrix([x+2*y+3*z=4, 5*x+6*y+7*z=8, 9*x+10*y+11*z=12],[x,y,x]);と書いても同じことですが、タイプ量の節約のためにも、またタイプミスを減らすためにもうまく名前を使うことは有益です。行列で表現された連立一次方程式 Ax = b に対して、行列 (A|b) のことを、拡大係数行列と言いましたが、maxima でも関数 augcoefmatrix によって、拡大係数行列を求めることができます。ただし、(A|b) ではなく、(A| − b) を求めるので、注意する必要があります。

(%i4) Ab : augcoefmatrix(eq1,xx);
1 2 3−4−8 (%o4)  5 6 7
9 10 11 −12
さて、連立一次方程式の解の様子を知るには、拡大係数行列を行基本変形で階段行列に変形して係数行列の階数 rank(A) と拡大係数行列の階数 rank(Ab) を比較してみればよかったですね。maxima でそれをする方法についてはすでに説明しました。早速やってみます。

(%i5) echelon(Ab); 
1 2 3 −4(%o5)  0 1 2 −3 
0 0 0 0(%i6) rank(A);(%o6) 2(%i7) rank(Ab);(%o7) 2
得られた階段行列の形からもわかりますが、rank(A) = rank(Ab) = 2 なので、この連立一次方程式 eq1
は、未知数個数 n = 3 から rank(A) = 2 を引いただけの、すなわち 3 - 2 = 1 個の任意定数を含む無限個の解を持つことがわかります。

2.5. 連立一次方程式を解く. 連立一次方程式が解を持つことがわかり、その解の様子が予想できたなら、今度は具体的に解を求めたくなりますね。解を求めることも、maxima なら簡単に実行できます。上の連立一次方程式 eq1 の解を、maxima の関数 solve で求めて見ましょう。
(%i8) solve(eq1, xx);
Dependent equations eliminated: (3)(%o8) [[x = %R1 − 2, y = 3 − 2%R1, z = %R1]]
ここで、%R1 と表示されているものが任意定数です。次の例の様に、解を持たない方程式をいきなり solveで解こうとすると、エラーメッセージを貰うことになるので、事前に解の様子を調べておいた方が良いでしょう。

(%i9) kill(ALL);(%o0) DONE

maxima による行列計算超入門(%i1) eq2 : [x + 2*y = 3, 4*x + 5*y = 6, 7*x + 8*y = 0];(%o1) [2y + x = 3, 5y + 4x = 6, 8y + 7x = 0](%i2) xx : [x,y];(%o2) [x, y](%i3) solve(eq2, xx);
Inconsistent equations: (1)-- an error. Quitting. To debug this try DEBUGMODE(TRUE);
実際、(%i4) A : coefmatrix(eq2,xx);1 2(%o4)  4 5 
7 8(%i5) Ab : augcoefmatrix(eq2,xx);
1 2 −3(%o5)  4 5 −6 
7 8 0(%i6) echelon(Ab); 01 87(%o6)  0 1 −14 
0 01(%i7) rank(A);(%o7) 2(%i8) rank(Ab);(%o8) 3より、rank(A)6=rank(Ab) ですから、この連立一次方程式 eq2 は解をもちません。

1112足立健朗

3. もっと高度な機能について
maxima では、これまで述べてきたことに加えて、さらに色々なことができます。講義ですでに習った
ことに関連する機能としては、例えば余因子行列を求めるとか、三角化するとかいったものがあります。また、ベクトルについても内積を求めたりすることなどができます。一次独立なベクトルの正規直交化といったことや、行列の固有値、固有ベクトルを求めるといったこともできます。この超入門編では, そう言った進んだ話題については取り上げることができませんでしたが、興味のあるかたは、maxima のマニュアルを読んだり、このページにに置いてある「行列計算における数式処理ソフト maxima の利用について」 などを参考にして、より高度な利用にチャレンジしてみて下さい。

maxima による行列計算超入門

E-mail address: kenrou@yo.rim.or.jp

13