Re: Embedding maxima



On Sat, 26 Feb 2005 10:28:51 -0800 (PST), Robert Dodier
 wrote:
>  - To see the Lisp representation of a Maxima expression,
>    type the expression at the prompt (say at %i99), and then
> 
>    :lisp $%i99
> 
>    to see it. Likewise ``:lisp $%o99'' shows the representation
>    of %o99 (usually different from %i99). I believe this might
>    help you see how to construct arguments for Maxima functions.

I did something similar. At the lisp prompt, I typed something like this:

MAXIMA> '#$ diff(x^2, x) $

Notice the quote in front. This gives a call to MEVAL* on the sexp
equivalent of the Maxima expression.

>  - By the way, ``(displa $foo)'' (note the absence of ``y'')
>    prints $foo in Maxima notation.

I wrote a function which binds print2d to false and uses
WITH-OUTPUT-TO-STRING to return a 1D pretty-printed version of Maxima
expressions. Am I duplicating effort? Is there some function similar
to DISPLA which takes a stream argument, for example?

>  - There is some description of Lisp/Maxima interactions in
>    maxima/doc/info/Help.texi under the heading "Lisp and Maxima";
>    ``? lisp and maxima'' or ``describe ("lisp and maxima")'' should
>    show it. That text was recently revised (January 2005);
>    I recommend you ignore any older version. Actually, I will be
>    indebted to you if you would take a look at "Lisp and Maxima"
>    and let me know what it's lacking from your point of view.

What I would really like to do is interpolate Lisp values into Maxima
expressions. I'll give you a concrete example:

I have a ball shot out of a cannon, and its 2D velocity vector is
called v in my lisp code. It uses a class that I defined. The motion
of the ball, until it hits the ground, can be approximated with these
parametric equations:

x(t) := (x-component v)*t + xi
y(t) := (1/2)*g*t^2 + (y-component v)*t + yi

The problem is that I don't know how to properly interpolate the
"(x-component v)" parts into Maxima's syntax, so I'm reduced to doing
stuff like this:

(defun make-vector-polar (r theta)
 "Make a vector given polar coordinates"
 (let ((x ($ratsimp `((mtimes simp) ((%cos simp) ,theta) ,r)))
       (y ($ratsimp `((mtimes simp) ((%sin simp) ,theta) ,r))))
   (make-vector x y)))

This gets very ugly when the expressions get more complicated:

(defmethod set-x ((body free-body) x)
  "Set the X coordinate of a free body by calculating the proper time
t and setting t to it"
 (let ((time ($ratsimp `((mtimes simp)
                         ((mexpt simp) ,(x-component (velocity body)) -1)
                         ((mplus simp)
                          ((mtimes simp)
                           -1
                           ,(point-x (initial-coordinates body)))
                          ,x)))))
   (set-time body time)))

In both cases, I was just taking the output from the '#$ ... $ trick
above, downcasing it, and using backquoting to interpolate my own
values before Maxima simplifies it. This is not pleasant to code or to
read.

Alternately, I could try calling READ-FROM-STRING on a string I build
up with FORMAT, but that smells like another ugly hack.

Got any wisdom to impart on the matter?

-Peter