MATH LIBRARY version 2.10
An almost complete math package for dealing with
matrices and polynomials
Written in SysRPL and Machine Language
Library number 1211
By Cesar Augusto Rorato Crusius - 1994
NOTICE....................................................3
This program is Post-Cardware.........................3
ABOUT.....................................................4
LIMITATIONS and BUGS......................................5
BE CAREFUL............................................5
USER MODE.............................................5
GX COMPATIBILITY......................................5
MATH DATA TYPES...........................................6
VERSION DIFFERENCES.......................................7
Version 1.00 and 1.10.................................7
Version 1.10 and 1.20.................................7
Version 1.20 and 1.21.................................8
Version 1.21 and 1.30.................................8
Version 1.30 and 2.00.................................9
Version 2.00 and 2.10.................................10
SPEED MARKS (version 2.00)................................11
MATH speed versus HP speed :-)........................12
LIBRARY COMMANDS DESCRIPTION..............................14
MADD..................................................14
MSUB..................................................14
MMLT..................................................14
MDIV..................................................14
MPWR..................................................15
MRoot.................................................15
MFCTP.................................................15
MCOEF.................................................15
MEVL..................................................15
MDER..................................................16
ZTRIM.................................................16
MDET..................................................16
MINV..................................................16
MTRN..................................................17
MIDN..................................................17
A<->L.................................................17
PR|L..................................................17
FRPRC.................................................17
ADPOL.................................................19
STDL..................................................19
EVALUES...............................................20
SVALUES...............................................20
MADJ..................................................20
MINOR.................................................20
MGET..................................................21
MPUT..................................................21
Row-..................................................21
page 1
Row+..................................................22
Col-..................................................22
Col+..................................................23
RSwp..................................................23
CSwp..................................................23
MSIZE.................................................23
MTRACE................................................24
ABOUT.................................................24
UTILITY PROGRAMS..........................................25
MVID..................................................25
MFLAG.................................................25
APPLICATION NOTES.........................................26
MEVL hints and suggestions............................26
Interesting application of A<->L......................26
Rank of a matrix......................................27
Computing the determinant in a faster way.............27
Successive divisions..................................27
Ackermann's formula...................................27
SPLIT.................................................28
A NOTE ON THE METHODS.....................................29
THANKS TO.................................................30
page 2
NOTICE
* The program MATH 2.10 and the documentation in this
file are provided "as is", and are subject to change
without notice. I give no warranty of any kind with
regarded to the software or documentation, including,
but not limited to, the implied warranties of
merchantability and fitness for a particular purpose.
Cesar Augusto Rorato Crusius shall not be liable for any
error or for incidental or consequential damages in
connection with the furnishing, performance, or use of
this software and documentation.
* Sale of this material is not allowed without prior
written permission of Cesar Augusto Rorato Crusius.
* Non commercial distribution allowed, provided that the
original documentation is preserved unchanged.
* Modified versions are NOT allowed.
* Use of any part of MATH library code is not allowed
for any purpose, except, of course, when used directly
from the MATH library. You cannot reproduce any part of
MATH library code for any purpose without prior written
permission of Cesar Augusto Rorato Crusius. Use of MATH
library in commercial or shareware programs is not
allowed.
This program is Post-Cardware
* If you use and enjoy this excellent program you MUST
send me a post-card. It will not cost too much, and I'll
appreciate a lot ! Send it to the following address:
Cesar Crusius
Caixa Postal 5193
Trindade - Florianopolis - SC
ZIP CODE 88040-970
this address will work only 'til Jan 1996. So hurry up !
page 3
ABOUT
As we know, many times we need to perform
calculations only with numbers. Many times we need to do
polynomial calculus (multiplication, division and so
on). Then, if we go one step ahead, we will need to do
the same calculations with symbolic polynomials. As we
go deeper, we will need many more things: symbolic
matrices, matrices of polynomials, matrices of symbolic
polynomials, matrices of matrices, et cetera.
MATH library is the way to do all those things! You
can add a symbolic polynomial to a numerical matrix, and
you'll get the correct answer: a symbolic matrix. Now
you can get the inverse of the symbolic matrix, add a
polynomial to this matrix and so on... Let's take an
example. Let's do inv(sI-A) (familiar to engineers) in
two ways (consider A=[[1 2][3 4]]):
First method: using the symbol 'S'
2:'S' 1:{{'S-1' -2} 2:{{'S-4' 2}
1:[[1 2] MSUB {-3 'S-4'}} MINV {3 'S-1'}}
[3 4]] 1:'(S-1)*(S-4)-6'
The second method uses [1 0] as a polynomial for 'S':
2:[1 0] 1:{{[1 -1] -2} 2:{{[1 -4] 2}
1:[[1 2] MSUB {-3 [1 -4]}} MINV {3 [1 -1]}}
[3 4]] 1:[1 -5 -2]
As you can see, if you work with a lot of calculus
THAT is the program you need.
page 4
LIMITATIONS and BUGS
This program is very difficult to debug because of
its high complexity. You can do almost everything with
the commands. If you try to do something you think is
right and get a wrong answer, please notice me and I'll
try to fix the bug. Any suggestions are welcome.
BE CAREFUL
There are times when the program has no way to
discover what you are trying to do. As an example, take
{{A 1 2}}. What is that? A 1x3 matrix or a zero-degree
polynomial with the idependent coefficient equal to the
symbolic polynomial {A 1 2}? There's no way to discover.
The program will, in those cases, take the first choice.
So DO NOT try to add {{A 1 2}} with {{1 2}}, because the
program will think that you're trying to add two
matrices. Do {0 {A 1 2}} + {0 {1 2}} instead. This will
work correctly.
USER MODE
In the library commands description, sometimes I say
that you can assign some command to some key. When I say
that, I mean that you can STAY IN USER MODE and continue
to use the keys as if none command were assigned to them
if the arguments do not match those of the library
command.
GX COMPATIBILITY
As discovered by Michael Guravage, MATH may not work
correctly if installed on a RAM card that lies on the
second slot of a GX calculator. So, if you have a GX,
install MATH on the main memory or on the first slot.
page 5
MATH DATA TYPES
There are basically two kinds of data that you can use
with MATH library: numerical and symbolic data. You
represent numerical data with the "array" format of the
HP48. Symbolic data is represented just replacing the
"[]"s by "{}". Being that way, a numerical matrix for
MATH have exactly the same format as for the calculator.
Examples:
numerical 2x2 matrix: [[ 1 2 ][ 3 4 ]]
symbolic 2x2 matrix: {{ 1 2 }{ 3 A }}
Polynomials are represented as vectors, and the vector
elements are the coefficients of the polynomial.
Example: the polynomial x^3+2*x+3, for MATH, is [1 0 2
3]. Note that the polynomial variable is unknown! If you
have symbolic coefficients you must use the symbolic
format. Example: x^3+A*x^2+2*x+3 is represented as { 1 A
2 3 }.
page 6
VERSION DIFFERENCES
Version 1.00 and 1.10
Now the library is GX compatible! When the program
detects that it's being used on a GX, MRoot dispatches
to the GX own PROOT.
In version 1.0 MINV did not work correctly for 1x1
matrices. Now it does.
The program A<->L now works correctly when there are
complex numbers involved.
Some differences in MEVL, e.g. it can be used as PR|L
for matrices. It also dispatches to the system EVAL when
arguments are not matching.
Many commands now dispatch to some system commands when
arguments are not matching. Here are the list of the
commands: MRoot dispatches to SQRT, MEVL dispatches to
EVAL, MFCTP dispatches to XROOT and MDER dispatches to
"delta". I made this so I can assign these commands to
the corresponding system keys and I can stay in user
mode to perform normal calculations.
ADPOL accepts any combination of lists/polynomials and
execute MFCTP on the arguments that are polynomials.
When MFCTP receives a list it does nothing.
A lot of changes in FRPRC. You better read the command
description.
Version 1.10 and 1.20
MMLT and MDIV now works normally, i.e., there are no
more "element-by-element" product and MDIV does not
accept that Matrix/Array stuff.
MMLT now can multiply a symbolic polynomial by a matrix.
In earlier versions this was not allowed.
MDIV now can divide a symbolic matrix by anything but an
array. When dividing a polynomial by a zero-degree
polynomial the answer is a single polynomial. If the
remainder of a polynomial division is a zero-degree
polynomial, then the remainder is only a number, and not
a single-element array.
A correction to the old version manual brings up a new
capability of MEVL (it was already implemented in
page 7
version 1.10, but I forgot to mention it on the old
version manual :-). If you have a matrix of polynomials
you can execute MEVL exactly as if you have a
polynomial, i.e., every polynomial in the matrix will be
evaluated for the given point (and the point can be
anything: a matrix, another polynomial and so on).
EVECT and EVALUES commands added.
MADD and MSUB return numerical arrays when you add or
subtract a complex number from a matrix. In earlier
versions they return symbolic matrices.
Now the following commands test the matrix dimensions:
MADD, MSUB, MMLT, MDET and MINV. The test is not
complete, but make this commands much safer to use.
MEVL now treats a real number as a zero-degree
polynomial.
ZTRIM is now transparent to objects that are not
polynomials. When used on a zero-degree polynomial, the
answer is the zero-degree coefficient. ZTRIM can also be
used on a matrix.
Version 1.20 and 1.21
Some machine code added.
A<->L now accepts a list with symbolic elements. The
program computes the numerical value of the symbolic
elements before the transformation.
Version 1.21 and 1.30
MADJ command added, so now you don't need to invert a
matrix in order to compute its adjoint. MINOR command
added to compute the minor matrix.
Some utility commands added: MGET, MPUT, Row-, Row+,
Col- and Col+. These commands follows the same syntax as
for SX/GX GET and PUT, and Row+- & Col+- follows the
same syntax as for GX ROW+- and COL+-, so now you can
make a LOT of programs to deal with symbolic matrices.
MINV is now much faster, because now the matrix
determinant is computed in a very fast way. In fact, the
determinant of the matrix M is equal to the first row of
adj(M) times the first column of M!
page 8
Version 1.30 and 2.00
SPEED! Now MATH is the fastest polynomial math program
for the HP48 series! A lot of numerical polynomial tasks
are performed 99% in machine language. The speed is
improved by 1000% in many operations, such as MADD and
MMLT (take a look at MPWR). Because of the internal
representation for polynomials (arrays of long
complexes), the precision is greater too! BELIEVE IT OR
NOT, MATH's MEVL running under a version D HP48-SX is
MUCH FASTER THAN HP48-G's PEVAL !!! MADD for arrays is
FASTER THAN HP'S "+" !!!
SIZE! MATH 2.00 keeps almost the same size as MATH 1.30,
thanks to the new MRoot program. The new MRoot is a
little bit slower than the old one (the old and good
PROOT), but it's a good roots program too, and memory is
at a premium in my "dinosaur" HP48-SX version D. The new
MRoot can take the roots of polynomials with complex
coefficients! If you have a G(X), then MRoot will
dispatch to PROOT and change the output format to a
list.
MEVL can evaluate the nth-derivative (for any "n") of a
polynomial as well!
New commands added for numerical and symbolic matrices:
RSwp, CSwp, MSIZE and MTRACE. EVECT has gone, and
SVALUES (singular values) takes its place.
Some corrections on Row+ and Col+. MGET is now user-
proof (i think :-). MDET internally improved. It will
test for zero pivots, so if your matrix have many zeros
on the first row the program will execute A LOT faster.
MDIV now divides complex coefficient polynomials.
Some polynomial tasks will return simplified
polynomials, if possible, by transforming complex
polynomials into real ones. Example: If you execute MADD
with [ (1,1) (0,0) ] and [ (1,-1) (2,0) ], you will get
[ 2 2 ] instead of [ (2,0) (2,0) ].
MROOT now is MRoot (there is a MROOT command in G
series). But don't worry, your programs will keep
working, 'cause the XLIB number remains the same.
MGET and MPUT now accepts lists with symbolic elements.
The programs will compute the numerical value of the
symbolic elements.
page 9
Version 2.00 and 2.10
Bug in SVALUES fixed, and now it works :-)
MEVL now can compute the nth derivative of a symbolic
polynomial too. MDER now passes automatically through
symbolic matrices. MDIV now can divide a numerical
polynomial by a symbolic element, and can divide complex
coefficients polynomials.
Col+ now returns a numerical matrix if the input
arguments are two numerical matrices.
All commands ( except PR|L ) now works correctly with
LASTARG. MEVL will keep only the first element of the
stack. However, this feature eated more than a half
kbyte of your precious memory.
page 10
SPEED MARKS (version 2.00)
I made some speed measures to compare MATH 1.30 and
2.00, and here are the results. The tests were made on
my HP48 version D with 32k. Only MATH was on the calc,
so there were about 20k free. All LAST flags were
enabled (thus slowing the speed). When two lines are
presented for the same test, then the first line
contains the results for real polynomial tests, and the
second contains the results for complex polynomial
tests. Note that my calculator is an SX, so if you have
a GX you'll be even faster!
+----------------+---------+---------+-----------+
| command | v1.30 | v2.00 | improv (%)|
+----------------+---------+---------+-----------+
| V2 V1 MADD | 1.870 | 0.096 | 1847.92 |
| | 2.084 | 0.101 | 1963.37 |
+----------------+---------+---------+-----------+
| V2 V1 MSUB | 1.948 | 0.173 | 1026.01 |
| | 2.181 | 0.188 | 1060.17 |
+----------------+---------+---------+-----------+
| V2 V1 MMLT | 34.405 | 1.004 | 3326.79 |
| | 48.726 | 1.202 | 3953.74 |
+----------------+---------+---------+-----------+
| V2 V1 MDIV | 23.925 | 3.093 | 673.52 |
| | xxxxxx | 7.130 | xxxxxx |
+----------------+---------+---------+-----------+
| V1 2 MPWR | 103.658 | 0.575 | 17927.47 |
| | 145.514 | 0.820 | 17645.61 |
| [1 1] 10 MPWR | 25.690 | 0.617 | 4063.70 |
+----------------+---------+---------+-----------+
| V2 (1+j) MEVL | 1.709 | 0.177 | 865.54 |
| | 1.803 | 0.172 | 948.26 |
+----------------+---------+---------+-----------+
| V2 MDER | 1.033 | 0.707 | 46.11 |
+----------------+---------+---------+-----------+
| FRPRC | 87.067 | 18.385 | 373.57 |
+----------------+---------+---------+-----------+
| V1 MRoot | 10.051 | 11.151 | -9.86 |
| | xxxxxx | 32.799 | xxxxx |
+----------------+---------+---------+-----------+
| V1 MFCTP | 10.278 | 11.388 | -9.75 |
+----------------+---------+---------+-----------+
| V1roots MCOEF | 11.757 | 0.849 | 1284.81 |
+----------------+---------+---------+-----------+
| M1 MDET | 181.594 | 71.468 | 154.09 |
+----------------+---------+---------+-----------+
| M1 MINV | 903.567 | 196.638 | 359.74 |
+----------------+---------+---------+-----------+
| M2 EVALUES | 189.759 | 27.816 | 617.06 |
+----------------+---------+---------+-----------+
page 11
The vectors and matrices used for the test were:
V1real = [ 1 2 3 4 5 6 7 8 9 10 ]
V1comp = (1,1)*V1real
V2 = V1 ^ 2
[[ 1 2 0 4 0]
[ 5 3 4 0 6]
M2 = [ 0 2 5 6 2]
[ 0 3 2 -1 -1]
[-5 3 1 -2 8]]
M1 = [ 1 0 ] - M2
FRPRC test: in normal mode, numerator = [ 100 0 ] and
denominator = { [ 1 2 5 ] 3 [ 1 1 ] 3 [ 1 2 ] }
Speed improvement = 100*( 1.30/2.00 - 1 )
MATH speed versus HP speed :-)
Just kidding, I love HP calcs, but you must look at
this! Here are some speed comparsions between MATH
commands and the similar HP commands. The HP used for
the test was a version R HP48-G. The polynomials used
were:
real: P=[1 1] 40 MPWR
cmplx: C=[1 1] 40 MPWR (1,1) *
All results are in seconds. Take a special look at the
comparsion between PEVAL and MEVL.
+-------+-------+
| HP48G | MATH |
+-----------------------+-------+-------+
| P P + vs MADD | 0.275 | 0.134 |
+-----------------------+-------+-------+
| C C + vs MADD | 0.649 | 0.147 |
+-----------------------+-------+-------+
| P (1,1) PEVAL vs MEVL | 1.080 | 0.218 |
+-----------------------+-------+-------+
| C (1,1) PEVAL vs MEVL | 1.338 | 0.227 |
+-----------------------+-------+-------+
Please note two things:
i. MATH's MADD is faster AND more versatile than HP's
command "+" for vectors: when adding two complex vectors
(polynomials for MATH), MADD will return a real one if
possible.
ii. MATH's MEVL is faster AND more versatile than HP's
command PEVAL: MEVL can evaluate the polynomial
page 12
derivatives AND will return a real value if possible
(i.e. if the imaginary part of the result is zero).
page 13
LIBRARY COMMANDS DESCRIPTION
In this section a complete description of the library
commands will be given. You can use any of the library
commands to make your own programs in user or SysRPL.
What I'm trying to say is that I will NOT change the
library ID or the XLIB numbers. The only command that
can have it's XLIB number changed is ABOUT.
MADD
Takes two arguments and try to add them. If one argument
is a matrix M and the other is anything but a matrix
(x), the program will perform the sum xI+M. If x is a
real number and M is a numerical matrix, the answer will
be a numerical matrix, as expected. Anything is allowed
(matrices of matrices of matrices of polynomials, and so
on...).
If you assign this program to the "+" key, be aware that
the following operation won't be carried out in the USER
mode:
{ 1 2 3 } 3 + ---> { 1 2 3 3 }
Instead, you'll get { 1 2 6 }.
MSUB
Takes two arguments and try to subtract them. If one
argument is a matrix M and the other is anything but a
matrix (x), the program will perform xI-M or M-xI (it
will do what you asked for). Anything is allowed.
This program can be assigned to the key "-".
MMLT
Multiplication in numerical/symbolic form. You can do
almost anything you want, e.g. multiply a numerical
matrix by a symbolic polynomial, or a numerical
polynomial by a symbolic polynomial. This program can be
assigned to the key "*".
MDIV
Divides level 2 object by level 1 object. You cannot
divide a matrix by an array, and level 1 object cannot
be a symbolic matrix. If the arguments are not matching,
the command dispatches to the HP own "/". When dividing
a polynomial by another, the answer will be the result
of the division on level 2 and the remainder on level 1.
If the remainder is a zero-degree polynomial, it will be
given as a number. If you divide a polynomial by a zero-
page 14
degree polynomial, the answer will be a single
polynomial (obviously the remainder will be zero).
MPWR
Takes an object in level 2 and raises it to the nth
power, where n is the value of the real number in level
1. This program can be assigned to the user key "y^x"
and you won't need to leave the user mode for the normal
operation of the key.
MRoot
Takes a numerical polynomial in level 1 with real or
complex coefficients and returns a list with the
polynomial roots. If the polynomial have zero degree,
then MRoot returns an empty list.
You can assign this command to the user key SQRT.
MFCTP
Takes a polynomial (like MRoot, but only real
coefficients are allowed) in level 1 and factorizes it,
returning the list of the polynomials. If the argument
is a list the program will simply do nothing. Note that
the leading coefficient of the factored polynomial will
be ONE no matter the value of the leading coefficient of
the original polynomial.
You can assign this command to the key XROOT.
MCOEF
Takes a list of roots in level 1 and returns the
polynomial that have these roots. All the roots must be
numerical, and they must correspond to a real
coefficient polynomial. The leading coefficient of the
resulting polynomial will be always one.
MEVL
Takes a polynomial (or a matrix of polynomials) P in
level 2 (matrices of matrices of polynomials are
allowed, and so on) and any object x in level 1 and
computes P(x). P can be symbolic or numerical, and x can
be anything (another polynomial or even a matrix). If
the object on level 2 is a real number, MEVL will simply
drop the level 1 object.
If you want to evaluate the nth-derivative of a
polynomial, add a hex-string with the value of "n" in
the arguments. Example:
page 15
3: [ 1 2 3 4 5 ]
2: 12
1: # 3d
MEVAL will compute the value of the 3rd derivative of
the polynomial [ 1 2 3 4 5 ] at the point 12. It will
return, in this case,
1: 300
You can assign this command to the key EVAL, but be
aware -> this is a "strange" command. Strange things can
happen if you try to use MEVL as the HP EVAL when there
are more than one element in the stack (e.g., a list of
variables on level 2 and anything on level 1), because
MEVL will think that the list is a polynomial, and so
on...
If you have a G(X), please note that MEVL is FASTER THAN
PEVAL.
MDER
Takes a polynomial in level 1 and computes its
derivative. The polynomial can be symbolic.
You can assign this command to the derivative key.
ZTRIM
Removes the left zeros of a polynomial or a matrix of
polynomials. If the object is not a polynomial, nothing
happens. If the result is a zero-degree polynomial, then
ZTRIM will return only the first element of this
polynomial.
MDET
Calculate the determinant of a square matrix. The matrix
can contain anything: polynomials, symbolic elements or
even matrices(!).
MINV
Calculate the inverse of a square matrix. You can have
anything on the matrix. The program returns a numerical
matrix if the input is a numerical matrix. If the input
is a symbolic matrix, the program returns, in level 2,
the adjoint matrix and, in level 1, the determinant. As
we know, the inverse is: adjoint matrix divided by the
determinant. Uses Faddeev method for symbolic matrices.
You can assign this command to the key "1/x".
page 16
MTRN
Calculate the transposed matrix. The matrix can be
either symbolic or numerical.
MIDN
Creates an identity matrix with the dimension of level 1
and with the diagonal elements equal to the level 2
element.
A<->L
Transform a symbolic/numerical poly/matrix into a
numerical/symbolic poly/matrix. The program will pass
the HP-command ->NUM to every element on a symbolic
representation, so now you can do things like
{ 1 '1/3' } ---> A<->L ---> [ 1 .3333... ]
PR|L
Given a list on level 2 and a program on level 1,
executes the program on every element of the list. This
program has a maximum depth of 2. What does it means?
The "depth" of PR|L is the "maximum recursivity depth"
of the program. So a "depth" of 2 means that PR|L will
pass the program through lists that are in the original
lists, but not through lists into these ones. See the
following examples:
{ 2 } << 2 + >> PR|L { 4 }
{{ 2 }} << 2 + >> PR|L {{ 4 }}
{{{ 2 }}} << 2 + >> PR|L {{{ 2 2 }}}
If you want to override this depth limit, simply add one
more parameter (a binary integer or a hex string)
containing the maximum depth wanted. Example:
{{{ 2 }}} << 2 + >> #3 PR|L {{{ 4 }}}
FRPRC
There are two types of partial fractions: the normal
type and the "Z-type". In the normal type, the
numerators' degrees are smaller than the denominators'
degrees. In the "Z-type", the numerators can have the
same degree as the denominators (very useful for Z-
transforms). User flag 31 control the current mode of
operation. If flag 31 is SET, then the normal type is
used, otherwise "Z-type" is used.
page 17
Level 1 can be a numerical polynomial or a list of
numerical polynomials representing Q. Example: if
Q=(x+1)(x+2)x^2 the list of level 1 could be:
{ [ 1 1 ] [ 1 2 ] [ 1 0 ] 2 } or
[ 1 3 2 0 0 ]
You must note that the leading coefficient of the
denominator polynomial MUST BE ONE! If this is not the
case, you must re-arrange the polynomials to get the
correct denominator polynomial. Complete example in
normal type (don't forget to set flag 31): calculate the
partial fractions of
(x+1)/((x+4)^2 * (x+2) * x)
2: [ 1 1 ]
1: { [ 1 4 ] 2 [ 1 2 ] [ 1 0 ] }
the output of FRPRC is
1: {{ [ -.15625 ] [ 1 4 ] 1 }
{ [ -.375 ] [ 1 4 ] 2 }
{ [ .125 ] [ 1 2 ] 1 }
{ [ .03125 ] [ 1 0 ] 1 }}
so the answer is
-.15625 .375 .125 .03125
-------- - -------- + ----- + ------
(x+4) (x+4)^2 x+2 x
If you want to use the "Z-type" partial fractions, you
must first clear flag 31. To use this mode of operation
there is one constraint to the numerator: it must have a
degree higher than zero, and the zero-order coefficient
must be zero. If you think that that's too bad, remember
that when you calculate the step response in Z you must
multiply the numerator by Z. So, if you use this mode to
work in Z-domain, this constraint will be not a problem
at all. The answer will always have its numerators with
the zero-order coefficients equal to zero (better for
inverse Z-transforms). Complete example: calculate the
partial fractions of
z/(z-1)(z-.5)
With flag 31 cleared, the stack must be
2: [ 1 0 ]
1: { [1 -1] [1 -.5] }
The program FRPRC will give you the answer:
page 18
1: {{ [ 2 0 ] [ 1 -1 ] 1 }
{ [ -2 0 ] [ 1 -.5 ] 1 }}
So the answer is
2z 2z
---- - ----
z-1 z-.5
SOME DIFFERENCES FROM MATH 1.00: If you already have
MATH 1.00, you'll soon notice that complete answers are
always given. I did that because it seems to be better
for the user and certainly it is better to make programs
that use FRPRC. The old style FRPRC that takes a binary
integer in level 1 is not allowed anymore.
A bug or a limitation? :-) Try to, whenever possible,
use the list format for the denominator. If you don't,
*strange* things may happen, as discovered by Tyson
Leistiko. Example: try to perform, in the normal mode,
the following partial fractions:
(a) -> [ 1 ] / [ 1 8 13 6 ]
(b) -> [ 1 ] / { [ 1 6 ] [ 1 1 ] 2 }
As you will note, the answers are different. Why?
Because MRoot isn't precise enough to identify the
multiple roots in -1 in the polynomial [ 1 8 13 6 ].
ADPOL
Make a FRPRC list from lists/polynomials.
Examples:
2: { [ 1 0 ] }
1: [ 1 0 ] -> ADPOL -> 1: { [ 1 0 ] 2 }
2: [ 1 2 1 ]
1: [ 1 2 5 ] -> ADPOL -> 1: { [ 1 2 5 ] 1 [ 1 1 ] 2 }
Note: one argument at least must be a numerical
polynomial.
STDL
Prepares a list to be used by FRPRC (the program FRPRC
automatically calls this program, so you will only use
it if you will build your own programs).
Example:
1: { [ 1 0 ] [ 1 2 ] 2 [ 1 0 ] 3 [ 1 2 ] 5 [ 1 4 ] }
page 19
STDL gives
1: { [ 1 0 ] 4 [ 1 2 ] 7 [ 1 4 ] 1 }
EVALUES
Takes a numerical square matrix (real or complex) on
level 1 and returns the list of the Eigenvalues of the
matrix. Example:
1: [[ 3 -1 1 ]
[ -1 5 -1 ]
[ 1 -1 3 ]]
EVALUES will return
1: { 2 3 6 }
This program uses Faddeev's method to find the
characteristic polynomial of the matrix and then
executes MRoot. This program is slower than GX's EGVL.
So, if you have a GX, you may want to use GX's own
command. The fact is that an SX owner can build his
programs using MATH's EVALUES and the programs will run
without modification on any GX with MATH 1.20 or newer
installed.
SVALUES
Takes a numerical matrix (real or complex) on level 1
and returns the list of the singular values of the
matrix. Example:
1: [[ 3 -1 1 ]
[ -1 5 -1 ]]
SVALUES will return
1: { 2.63787896258 5.57149841414 }
MADJ
Computes the adjoint matrix. One more time, the input
matrix can have anything as its elements. Uses Faddeev's
method.
MINOR
Computes the minor matrix. You must put in level 3 the
matrix, in level 2 the row and in level 1 the column to
be removed. Example:
page 20
3: { { 1 2 } { c d } { f 5 } }
2: 2
1: 2
MINOR will give you
1: { { 1 } { f } }
MGET
Pick an element from a matrix/polynomial. As in MPUT,
symbolic matrices can have ANY NUMBER OF dimensions! The
command follows the same syntax as the HP command GET.
Example:
2: { { { { A B } } { { C D } } } }
1: { 1 2 }
MGET will give
1: { { C D } }
MPUT
Puts an element into a matrix/polynomial. Note that only
numbers can be putted into numerical matrices. Another
important thing to note is that symbolic matrices can
have ANY NUMBER OF dimensions, and not only two! The
command follows the same syntax as the HP command PUT.
Let's do an example with a symbolic matrix with four
dimensions:
3: { { { { 1 2 } } { { 3 4 } } } }
2: { 1 2 1 2 }
1: A
MPUT will give
1: { { { { 1 2 } } { { 3 A } } } }
WARNING: In this version MPUT does not perform ANY tests
on the giving index! If you give an invalid index you
may (and certainly will) loose your memory!
Row-
Removes a row from a matrix. The program returns in
level 2 the modified matrix and, in level 1, the removed
row. If the original matrix has only one row, the
program will return the unity matrix [[1]] or {{1}}.
Example:
page 21
2: { { A B } { C D } { E F } }
1: 2
Row- will give you
2: { { A B } { E F } }
1: { C D }
Row+
Puts one or more rows into a matrix. You must put in
level 3 the original matrix, in level 2 the row (or
matrix of rows) and in level 1 the line where the rows
will be inserted. If the number in level 1 is greater
than the matrix dimensions, then the row(s) will be
inserted at the end of the matrix. Example:
3: [ [ 1 2 ] [ 3 4 ] ]
2: { A B }
1: 2
Row+ will give
1: { { 1 2 } { A B } { 3 4 } }
Another example:
3: { { 1 2 } { C 4 } { x y } }
2: { { a b } { c d } }
1: 3
Row+ will give
1: { { 1 2 } { C 4 } { a b } { c d } { x y } }
Note that any combination of symbolic/numerical matrices
are allowed.
Col-
Removes a column from a matrix. The program returns in
level 2 the modified matrix and, in level 1, the removed
column. If the original matrix has only one column, the
program will return the unity matrix [[1]] or {{1}}.
Example:
2: { { A B } { C D } { E F } }
1: 2
Col- will give you
page 22
2: { { A } { C } { E } }
1: { B D F }
Col+
Puts one or more columns into a matrix. You must put in
level 3 the original matrix, in level 2 the column (or
matrix of columns) and in level 1 the line where the
columns will be inserted. If the number in level 1 is
greater than the matrix dimensions, then the column(s)
will be inserted at the end of the matrix. Example:
3: [ [ 1 2 ] [ 3 4 ] ]
2: { A B }
1: 2
Col+ will give
1: { { 1 A 2 } { 3 B 4 } }
Another example:
3: { { 1 2 } { C 4 } { x y } }
2: { { a b } { c d } { e f } }
1: 3
Col+ will give
1: { { 1 2 a b } { C 4 c d } { x y e f } }
Note that any combination of symbolic/numerical matrices
are allowed.
RSwp
Exchange (swap) two rows of a matrix. The level 3 must
contain the matrix and the levels 2 and 1 the index of
the rows to be swapped.
CSwp
Exchange (swap) two columns of a matrix. The level 3
must contain the matrix and the levels 2 and 1 the index
of the columns to be swapped.
MSIZE
No more SIZE EVAL for polynomials and vectors! MSIZE
will give you the size of the object in level 1. If the
object is a polynomial (or a vector), then it will
return just a number. If it is a matrix, MSIZE will
return a list with the number of rows and columns.
page 23
MTRACE
Computes the trace of a square matrix, i.e., the sum of
the elements of the matrix diagonal. Of course it will
work for symbolic matrices ;-)
ABOUT
Shows my name !!! :-)
page 24
UTILITY PROGRAMS
Included with the package are some utility programs.
Here is the description:
MVID
If you do not use my Control Package, then this program
can be useful. Execute CNVID once or twice, until
"(S/Z)MOD" appear on the top of the screen. The
annunciators indicate what is the current type of
partial fractions and the current MATH version.
MFLAG
Use MFLAG to change the type of partial fractions
performed without have to (re)set the flag 31 by hand.
Again, if you have Control Package you'll not need this
program.
page 25
APPLICATION NOTES
MEVL hints and suggestions
This program can be used as PR|L if you have a symbolic
matrix in level 2 and a program in level 1. In this
case, the program will be evaluated for every matrix
element, just as PR|L does.
This program can be very useful for other tasks.
Example: if you have the polynomial x^3 + 2*x^2 + 3 and
want to make the variable substitution x=s+1, you can
get the polynomial in s by typing:
2: [ 1 2 0 3 ]
1: [ 1 1 ]
Now you execute MEVL (evaluates the polynomial when x is
another polynomial) and get the answer:
1: [ 0 1 5 7 6 ]
Of course you can get the polynomial in x back by
evaluating the s polynomial at [ 1 -1 ]
1: [ 0 0 1 2 0 3 ]
The leading zeros appears due to the evaluating
algorithm. The answer is right anyway...
Another thing that you can do with MEVL is to transform
a numerical polynomial into a symbolic polynomial.
Example:
2: [ 1 2 3 ]
1: 'S'
MEVL will return '(S+2)*S+3'. Beside the fact that
that's an "unusual" format for symbolic polynomials, the
answer is right. And, as you see, this format is faster
to evaluate and give better results than the "standard"
format.
Interesting application of A<->L
A suggestion: when you get the inverse of some matrix,
use A<->L and evaluate the program << ->Q >> over it (if
you have a G series calculator you can simply execute
the command ->Q). As an example, try to do this with the
matrix [[3 1][-4 1]]. The symbolic matrix will be much
better to visualize.
page 26
As you may note, the inverse procedure can be useful
when entering matrices like [[ 1/3 1 ] [ 0 1/7 ]].
Simply enter {{ '1/3' 1 }{ 0 '1/7' }} (some may prefer
the matrix editor to this method). After that, use A<->L
and get the numerical matrix.
Rank of a matrix
If you have a GX you have a command to compute the rank.
But if you haven't, you can compute the rank by checking
the number of non-zero singular values of the matrix.
The following program will return the rank of a matrix:
<< SVALUES ZTRIM SIZE >>
Computing the determinant in a faster way
MDET now tests for zero pivots. So, if you have, on your
matrix, a row with many zeros, swap (using RSwp) this
row and the first. The determinant will be computed in a
faster way. But don't forget to negate the result
accordingly !
Successive divisions
This program is very useful, for example, if you want to
simulate a digital system. It takes the numerator from
the 3rd level, the denominator from the 2nd level and
the number of divisions to carry out in the first level.
The program will return a list with the values of the
divisions.
<< OVER SIZE [ 0 ] SWAP RDM 4 ROLL MADD -> Q N P
<< { } 1 N
START
P Q MDIV [ 1 0 ] MMLT
'P' STO 1 GET DUP 1 DISP +
NEXT
>>
>>
Ackermann's formula
Suppose you have a SISO system dx=Ax+Bu and you want to
use the control law u=Kx to place the poles of the
closed-loop system at a certain location. Then you can
use Ackermann's formula to compute the gain matrix K.
This program computes this gain matrix using Ackermann's
formula and the following data:
3: A
2: B
1: { desired poles (MCOEF format) }
page 27
The program will give you the gain matrix K:
<< MCOEF -> A B P
<< B DUP 2 A SIZE 1 GET
START A ROT * SWAP OVER 1000 Col+
NEXT INV P A MEVL * SWAP TRN 0 * DUP
SIZE -1 PUT SWAP *
>>
>>
SPLIT
The following program, "SPLIT", is a perfect example of
how much work can be saved by using MATH and a little
programming. Suppose you have the polynomial fraction
P(s)/Q(s). Now you make s=jw, and you want to split the
original fraction into the real and imaginary parts,
Pr(w)/Qr(w) + j*Pi(w)/Qi(w). The following program will
do the task: it takes P and Q from the stack and returns
on level two the list { Pr Qr } and on level one the
list { Pi Qi }
<< [ (0;1) (0;0) ] ROT OVER
MEVL ROT ROT MEVL ZTRIM
DUP CONJ ROT OVER MMLT ROT
ROT MMLT RE OVER RE ZTRIM
OVER 2 ->LIST ROT IM ZTRIM
ROT 2 ->LIST
>>
Example: P(s)/Q(s) = 1/s(s+1)^2
2: [ 1 ]
1: [ 1 2 1 0 ]
After SPLIT you'll get
2: { [ -2 0 0 ] [ 1 0 2 0 1 0 0 ] }
1: { [ 1 0 -1 0 ] [ 1 0 2 0 1 0 0 ] }
So the decomposition is:
P(jw) -2 w^2 - 1
----- = --------------- + j*---------------
Q(jw) w^4 + 2*w^2 + 1 w^5 + 2*w^3 + w
page 28
A NOTE ON THE METHODS
MRoot uses Laguerre's method only. It works VERY well
for polynomials with distinct roots, and is satisfactory
for polynomials with multiple roots. If you want to know
more about this method try the book "A SURVEY OF
NUMERICAL MATHEMATICS", by Young and Gregory. If you
are using a G(X), then MRoot is simply your PROOT with
some modifications for interfacing with MATH.
I use Faddeev's method a lot of times in the program.
The method can be used to compute a lot of things of a
matrix: the characteristic polynomial, the adjoint, the
determinant and all the Eigenvectors. If you want to
know more about Faddeev's method try the book "MATRIX
THEORY", by Gantmacher.
page 29
THANKS TO
I want to thank the following people for their support
and suggestions:
Andre Hentz (andre@lcmi.ufsc.br)
Arie Leib Bukinsky (bukinsky@jct.al.il)
David Peterson (18084DEP@msu.edu)
Hoa Van Lai (imach@cc.utexas.edu)
Joe Horn (joehorn@hpcvbbs.external.hp.com)
Keith Maddock (madd0118@nova.gmi.edu)
Marcelo Rodrigues (marcelor@acs.bu.edu)
Marcus Kindel (kindel@inf.ufrgs.br)
Mario Mozgy (mozgy@diana.zems.etf.hr)
Michael Guravage (Michael.Guravage@cwi.nl)
Mika Heiskanen (mheiskan@delta.hu.fi)
Sean McNamee (seanmc@u.washington.edu)
Tyson Leistiko (eleistik@elee.calpoly.edu)
Vinicius Vasconcellos (cello@vortex.ufrgs.br)
page 30