1 # -*-mode: tcl; fill-column: 75; tab-width: 8; coding: iso-latin-1-unix -*-
3 # $Id: Matrix.tcl,v 1.4 2006-10-01 23:58:29 villate Exp $
5 ###### Matrix.tcl ######
6 ############################################################
7 # Netmath Copyright (C) 1998 William F. Schelter #
8 # For distribution under GNU public License. See COPYING. #
9 ############################################################
11 # In this file a matrix is represented by a list of M*N entries together
12 # with an integer N giving the number of columns: {1 0 0 1} 2 would give
13 # the two by two identity
15 proc comment
{args
} {
18 set mee
" } \] \[ expr { "
20 proc mkMultLeftExpr
{ mat n prefix
{ constant
"" } } {
21 #create a function body that does MAT (prefix1,prefix2,..) + constant
26 for { set i
0} { $i < $n} {incr i
} { append vars
" $prefix$i" }
36 append ro
" $op $v*\$$prefix$j"
38 if { $j == [expr {$n -1}] } {
40 if { "[lindex $constant $k]" != "" } {
41 append ro
" + [lindex $constant $k] "
44 append ans
[concat \[ expr [list $ro] \]]
49 # puts [list $vars $ans]
50 return [list $vars $ans]
53 proc mkMultLeftFun
{ mat n name
{ constant
""} } {
54 set expr [mkMultLeftExpr
$mat $n _a
$constant]
55 set bod1
[string trim
[lindex $expr 1] " "]
56 # set bod "return \"$bod1\""
57 set bod
[concat list [lindex $expr 1]]
58 proc $name [lindex $expr 0] $bod
61 proc rotationMatrix
{ th ph
} {
63 [expr {cos
($ph)*cos
($th)}] [expr {- cos
($ph)*sin
($th)}] [expr {sin
($ph)}] \
64 [expr {sin
($th)}] [expr {cos
($th)}] 0.0 \
65 [expr {- sin
($ph)*cos
($th)}] [expr {sin
($ph)*sin
($th)}] [expr {cos
($ph)}]]
68 proc rotationMatrix
{ thx thy thz
} {
71 [expr { cos
($thy)*cos
($thz) } ] \
72 [expr { cos
($thy)*sin
($thz) } ] \
73 [expr { sin
($thy) } ] \
74 [expr { sin
($thx)*sin
($thy)*cos
($thz)-cos($thx)*sin
($thz) } ] \
75 [expr { sin
($thx)*sin
($thy)*sin
($thz)+cos
($thx)*cos
($thz) } ] \
76 [expr { -sin($thx)*cos
($thy) } ] \
77 [expr { -sin($thx)*sin
($thz)-cos($thx)*sin
($thy)*cos
($thz) } ] \
78 [expr { sin
($thx)*cos
($thz)-cos($thx)*sin
($thy)*sin
($thz) } ] \
79 [expr { cos
($thx)*cos
($thy) } ] ]
82 # cross [a,b,c] [d,e,f] == [B*F-C*E,C*D-A*F,A*E-B*D]
83 # cross_product([a,b,c],[d,e,f]):=[B*F-C*E,C*D-A*F,A*E-B*D]
84 # cross_product(u,v):=sublis([a=u[1],b=u[2],c=u[3],d=v[1],e=v[2],f=v[3]],[B*F-C*E,C*D-A*F,A*E-B*D]);
85 # the rotation by azimuth th, and elevation ph
86 # MATRIX([COS(TH),SIN(TH),0],[-COS(PH)*SIN(TH),COS(PH)*COS(TH),SIN(PH)],
87 # [SIN(PH)*SIN(TH),-SIN(PH)*COS(TH),COS(PH)]);
89 proc rotationMatrix
{ th ph
{ignore
{} } } {
95 [expr {-cos($ph)*sin
($th) } ]\
96 [expr {cos
($ph)*cos
($th) } ]\
98 [expr {sin
($ph)*sin
($th) } ]\
99 [expr {-sin($ph)*cos
($th) } ]\
103 proc setMatFromList
{name lis n
} {
107 uplevel 1 set [set name
]($i,$j) $v
108 if { $j == $n } {set j
1; incr i
} else { incr j
}
112 proc matRef
{ mat cols i j
} {
113 [lindex $mat [expr {$i*$cols + $j}]]
116 proc matTranspose
{ mat cols
} {
118 set m
[expr {[llength $mat ] / $cols}]
119 while { $j < $cols} {
122 append ans
" [lindex $mat [expr {$i*$cols + $j}]]"
131 proc matMul
{ mat1 cols1 mat2 cols2
} {
132 mkMultLeftFun
$mat1 $cols1 __tem
133 set tr
[matTranspose
$mat2 $cols2]
134 set rows1
[expr {[llength $mat1] / $cols1}]
136 set upto
[llength $tr]
140 while { $j < $cols2 } {
141 append ans
" [eval __tem [lrange $tr $i [expr {$i+$cols1 -1}]]]"
146 # puts "matTranspose $ans $rows1"
147 return [matTranspose
$ans $rows1]
152 proc invMat3
{ mat
} {
153 setMatFromList xx
$mat 3
154 set det
[expr { double
($xx(1,1))*($xx(2,2)*$xx(3,3)-$xx(2,3)*$xx(3,2))-$xx(1,2)* \
155 ($xx(2,1)*$xx(3,3)-$xx(2,3)*$xx(3,1))+$xx(1,3)*($xx(2,1)*$xx(3,2)\
156 -$xx(2,2)*$xx(3,1)) }]
158 return [list [expr { ($xx(2,2)*$xx(3,3)-$xx(2,3)*$xx(3,2))/$det}] \
159 [expr { ($xx(1,3)*$xx(3,2)-$xx(1,2)*$xx(3,3))/$det}] \
160 [expr { ($xx(1,2)*$xx(2,3)-$xx(1,3)*$xx(2,2))/$det}] \
162 [expr { ($xx(2,3)*$xx(3,1)-$xx(2,1)*$xx(3,3))/$det}] \
163 [expr { ($xx(1,1)*$xx(3,3)-$xx(1,3)*$xx(3,1))/$det}] \
164 [expr { ($xx(1,3)*$xx(2,1)-$xx(1,1)*$xx(2,3))/$det}] \
166 [expr { ($xx(2,1)*$xx(3,2)-$xx(2,2)*$xx(3,1))/$det}] \
167 [expr { ($xx(1,2)*$xx(3,1)-$xx(1,1)*$xx(3,2))/$det}] \
168 [expr { ($xx(1,1)*$xx(2,2)-$xx(1,2)*$xx(2,1))/$det}]]
172 proc vectorOp
{ a op b
} {
175 set ans
[expr [list [lindex $a 0] $op [lindex $b 0]]]
176 while { [incr k
] < $i } {
177 lappend ans
[expr [list [lindex $a $k] $op [lindex $b $k]]]
181 ## endsource matrix.tcl