[comp.sys.handhelds] HP48 multiple analytic equation solver/iterater

eer36024@uxa.cso.uiuc.edu (Erik E. Reuter) (09/05/90)

o Introduction

          This program uses Newton's method generalized to
     multiple-dimensions to  numerically solve multiple linear
     or nonlinear equations.  It was written for the HP-48SX but
     should run on the HP-28S with a few minor changes.


o Use

          Download the directory to your HP 48-SX (or decipher it and
     type it into your 28S or 48SX).  Within the EQSLV directory are
     two programs of interest: AUTOS and MANS.
          To use AUTOS, enter your N equations into stack levels 3
     through N+3, a list containing the variables in level 2, and
     a list containing the initial guesses for each variable (in the
     order the variables are given in the list).  If you expect a
     complex root, you must enter a complex guess.  Then press the
     AUTOS button.  After a pause, you will get an answer.

o Examples

                 Solve:   x * ( y + z ) = 2
                          y * ( x + z ) = 4
                          z * ( x + y ) = 8

    AUTOS:

      5: 'x*(y+z)=2'
      4: 'y*(x+z)=4'
      3: 'z*(x+y)=8'                      
      2: { x y z }
      1: {(1,1),(1,1),(1,1)}  
         press AUTOS
 
    (Why that particular guess?  I tried (0,0) (0,0) (0,0) and got
     a divide by zero (pole at origin) so I tried again)
    
    out: [ (0,0.7746) (-4.E-25,1.2910) (-3.E-24,-3.8730) ]

    This corresponds to the root
      x = i*(3/5)^(1/2), y = i*(5/3)^(1/2), z = -i*(15)^(1/2)

    (Note that in this case, -4.E-25 , -3.E-24  correspond to
     0, they are not zero due to round-off error)

    MANS:

     You suspect there is another root somewhere.

     Enter the same input from above, and press MANS.  
     MANS will perform one iteration, then display:

     2:  [ (-.25, 1.25) (0.75,0.2499) (2.75,-1.75) ]
     1:  1

     At this point, you may inspect and change the variable
vector and then return it to level 2.  You may also change
the number of iterations to perform before stopping (which
defaults to 1), and return this to level one.  Press ITER.

You have reason to believe that the complex part of x&y have
negative magnitude, and z has a positive magnitude, so you change
the variable vector to
       [ (-.25, -1.25) (0.75,-0.2499) (2.75,+1.75) ]
       5
       ITER

  out comes: [(.004,-.665) (-.716,-1.078) (-5.868,34.73) ]

  Not too promising, but lets try another 2 iterations.

     2
     ITER

    [(.1834,-.7483) (-.297,-1.24) (-.382,3.888)]

  Hmmm, starting to look familiar.  Lets change the real parts to zero.

    [(0,-.7483) (0,-1.24) (0,3.888)]
    10
    ITER

  And we have our answer:
    [ (2.393E-81,-.7746) (5.E-81,-1.291) (3.E-80,3.873) }

corresponding to the root
  x = -i*(3/5)^(1/2), y = -i*(5/3)^(1/2), z = +i*(15)^(1/2)


o Conclusion

     I have tested the program, but cannot gurantee that it
is free of bugs (i.e., don't trust your thesis to its results). 
Also, I am sure the program can be improved upon
in speed, size, clarity, and features.  I would like to hear
any comments or questions, or improvements you have made, but
don't send suggestions (program them yourself!).


Erik Reuter
eer36024@uxa.cso.uiuc.edu

Cut below this line
---------------------------------------------------------


%%HP: T(3)A(R)F(.);

DIR

  AUTOS

    \<< INIT JACOBIAN

      DO BSTO ASTO

FERRSTO CALCIT

XERRSTO

      UNTIL DONE

      END X9

CLEANUP

    \>>

  MANS

    \<< INIT JACOBIAN

X9 1

      \<< SWAP OVER 1

SWAP ROT 'X9' STO

        START BSTO

ASTO CALCIT

        NEXT X9

SWAP

      \>> 'ITER' STO

      \<< CLEANUP

DROP

      \>> 'QUIT' STO

ITER { ITER QUIT }

ORDER

    \>>

  CLEANUP

    \<< PATH DUP SIZE

1 - GET EVAL

'EQSLV9' PGDIR

    \>>

  DONE

    \<< FERR9 DF9 \<=

XERR9 DX9 \<= OR

NITER9 0 \<= OR

    \>>

  XERRSTO

    \<< 0 1 N9

      FOR I9 B9 I9

GET ABS +

      NEXT 'XERR9'

STO NITER9 1 -

'NITER9' STO

    \>>

  CALCIT

    \<< B9 A9 / 'B9'

STO X9 B9 + 'X9'

STO

    \>>

  FERRSTO

    \<< 0 1 N9

      FOR I9 B9 I9

GET ABS +

      NEXT 'FERR9'

STO

    \>>

  ASTO

    \<< 1 N9 SQ

      FOR I9 FPR9

I9 GET \->NUM

      NEXT N9 N9 2

\->LIST \->ARRY 'A9'

STO

    \>>

  BSTO

    \<< 1 N9

      FOR I9 X9 I9

GET FV9 I9 GET STO

      NEXT 1 N9

      FOR I9 F9 I9

GET \->NUM

      NEXT N9 \->ARRY

NEG 'B9' STO

    \>>

  JACOBIAN

    \<< 1 N9

      FOR I9 1 N9

        FOR J9 F9

I9 GET FV9 J9 GET \.d

        NEXT

      NEXT N9 SQ

\->LIST 'FPR9' STO

    \>>

  INIT

    \<< 'EQSLV9' DUP

PGDIR CRDIR EQSLV9

DUP SIZE 'N9' STO 1

1 N9

      START DUP2

GET \->NUM PUTI

      NEXT DROP

OBJ\-> \->ARRY 'X9' STO

'FV9' STO N9 \->LIST

'F9' STO 1 N9

      FOR I9 F9 I9

GET EQ\-> - F9 I9 ROT

PUT 'F9' STO

      NEXT 25

'NITER9' STO

.00000001 'DF9' STO

.000000001 'DX9'

STO

    \>>

END

--

----------------------------------------------------------------------
| Erik Reuter | Internet: eer36024@uxa.cso.uiuc.edu | (217) 367-1721 |
----------------------------------------------------------------------