changeset 49:c5a7665ca140 octave-forge

Adding Ben Sapp's symbolic toolbox (but not GinaC, cln, or gmp on which it depends)
author pkienzle
date Wed, 14 Nov 2001 15:09:50 +0000
parents 0ef6cb6a66e0
children 08858f6d9127
files main/symbolic/INSTALL main/symbolic/Makeconf.add main/symbolic/Makefile main/symbolic/configure.add main/symbolic/doc/symbolic.html main/symbolic/ov-ex.cc main/symbolic/ov-ex.h main/symbolic/ov-sym.cc main/symbolic/ov-sym.h main/symbolic/ov-vpa.cc main/symbolic/ov-vpa.h main/symbolic/splot.m main/symbolic/symbols.cc main/symbolic/symbols.h
diffstat 14 files changed, 1975 insertions(+), 0 deletions(-) [+]
line wrap: on
line diff
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/main/symbolic/INSTALL	Wed Nov 14 15:09:50 2001 +0000
@@ -0,0 +1,29 @@
+
+Prerequisites
+-------------
+You will need GiNaC installed before you can install this package. Go to
+the GiNaC web site http://www.ginac.de and follow the download 
+instructions.  It will tell you how to get cln and also how to build 
+GiNaC once you have built cln.  
+
+You will also need a version of Octave that was compiled without the 
+-fno-rtti or -fno-exceptions.  Versions below octave-2.1.33 have these 
+options by default.  These options are typically loacated in the 
+Makeconf file in the top level directory.  After configure and before 
+compile you can remove these options if you want to use an older 
+version of octave. 
+
+Compiling
+----------  
+Make sure that the correct version of mkoctfile is in your path.  Then 
+just type gmake(or whatever you call you version of GNU Make) in the 
+top level directory.  
+
+Installing
+----------
+Just type "gmake INSTALL_PATH=/your/path install" and it will install 
+all the .oct files and .m files in /your/path.  Add /your/path to your 
+octave path.  Once you have it installed you will need to type symbols 
+at the octave command prompt each session to initialize the toolbox.  
+Then you can use all of the commands in the toolbox.  Command completion
+will not work on the commands until after yopu have used them once.  
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/main/symbolic/Makeconf.add	Wed Nov 14 15:09:50 2001 +0000
@@ -0,0 +1,1 @@
+@DEFHAVE_GINAC@
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/main/symbolic/Makefile	Wed Nov 14 15:09:50 2001 +0000
@@ -0,0 +1,34 @@
+
+sinclude ../../Makeconf
+
+ifndef MKOCTFILE
+# assumptions to make if not using ./configure script
+MKOCTFILE=mkoctfile
+HAVE_GINAC=1
+endif
+
+SRC=symbols.cc ov-ex.cc ov-sym.cc ov-vpa.cc
+OBJ=$(SRC:.cc=.o)
+
+%.o: %.cc ; $(MKOCTFILE) -v $(GINAC_CPP_FLAGS) -c $<
+
+ifdef HAVE_GINAC
+
+GINAC_CPP_FLAGS=$(shell ginac-config --cppflags)
+GINAC_LD_FLAGS=$(shell ginac-config --libs)
+
+all: symbols.oct
+
+symbols.oct: $(OBJ)
+	$(MKOCTFILE) -v -o $@ $(OBJ) $(GINAC_LD_FLAGS)
+
+else
+
+all:
+
+endif
+
+clean:
+	$(RM) *.o *.oct core octave-core *~
+
+
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/main/symbolic/configure.add	Wed Nov 14 15:09:50 2001 +0000
@@ -0,0 +1,12 @@
+
+AC_SUBST(DEFHAVE_GINAC)
+
+AC_DEFINE(have_ginac)
+AC_CHECK_PROG(have_ginac, ginac-config, yes, no)
+
+if test $have_ginac = no ; then
+    DEFHAVE_GINAC=
+    AC_MSG_WARN([GiNaC not found; symbolic toolbox not built])
+else
+    DEFHAVE_GINAC="HAVE_GINAC=1"
+fi
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/main/symbolic/doc/symbolic.html	Wed Nov 14 15:09:50 2001 +0000
@@ -0,0 +1,248 @@
+<!doctype html public "-//w3c//dtd html 4.0 transitional//en">
+<html>
+<head>
+   <meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1">
+   <meta name="GENERATOR" content="Mozilla/4.75C-SGI [en] (X11; U; IRIX 6.5 IP22) [Netscape]">
+</head>
+<body text="#000000" bgcolor="#FFFFFF" link="#0000FF" vlink="#FF0000" alink="#000088">
+<font size=+2>Octave Symbolic Manipulation Toolbox</font>
+<p>The Octave Symbolic Manipulation Toolbox is based upon&nbsp; <a href="http://www.ginac.de">GiNaC</a>
+.&nbsp;&nbsp; The goal is to simply provide the capabilities of GiNaC in
+the easy to use environment provided by Octave.
+<p><font size=+1>Limitations/Features</font>
+<br>Currently there is no support for symbolic matrices. I think it would
+require a few changes to the parser to do it nicely: for example:&nbsp;
+sym_matrix = [x+1, x+5; x^2+4,x^2+2*x+1];&nbsp; I could make a function
+like sym_matrix(the_rows,the_columns,x+1, ... )&nbsp; that returned a symbolic
+matrix but this would be a bit of a kludge.
+<p>In order to do exact arithmetic you need to deal with strings and the
+vpa command.&nbsp; For example:&nbsp; vpa("1")/vpa("7") is represented
+internally as exactly 1/7.&nbsp;&nbsp; However,&nbsp; vpa("1")/7 or 1/vpa("7")&nbsp;
+is an approximation to 1/7 that is accurate to roughly the accuracy of
+the current value of digits.
+<p>GiNaC throws exceptions when there are problems with computations.&nbsp;&nbsp;
+I handle some of them at this time, but I do not handle all of them.&nbsp;&nbsp;
+This can cause octave to terminate prematurely.&nbsp;&nbsp; For example,
+try vpa("1")/vpa("0").&nbsp;&nbsp; This will eventually be fixed.
+<p><font size=+1>Download and install</font>
+<p>You will need to install cln-1.0.1, GiNaC-0.8.0 and octave-2.1.33 or
+later to use this package.&nbsp; You may be able to get by with an earlier
+version of octave if you compiled without the "-fno-rtti -fno-exceptions"
+options.&nbsp;&nbsp; This package uses both exceptions and run-time type
+identification.&nbsp;&nbsp;&nbsp; There is an INSTALL file in the package
+which will tell you how to install the package.
+<p><font size=+1>Functions</font>
+<br>Below I provide a list of function that I have implemented or have
+plans to implement as of the latest release .&nbsp; If the function name
+is <font color="#009900">green</font><font color="#330000"> </font><font color="#000000">then
+the function is implemented and to the best of my knowledge there are no
+problems with it.&nbsp; If the function is </font><font color="#CC0000">red
+</font><font color="#000000">then it has not been implemented yet.&nbsp;
+If the function is </font><font color="#000099">blue</font><font color="#000000">
+then it has been implemented but is known not to work correctly.&nbsp;
+Blues will appear only very rarely.</font>
+<ul>
+<li>
+<font color="#009900">vpa</font>&nbsp; - create a variable precision arithmetic
+variable from a string, double, or an appropriate expression.</li>
+
+<li>
+<font color="#009900">sym</font>&nbsp; - create a symbolic variable</li>
+
+<li>
+<font color="#009900">is_vpa</font>&nbsp; - returns true if an object is
+a vpa object</li>
+
+<li>
+<font color="#009900">is_sym</font>&nbsp; - return true if the argument
+is a symbolic variable</li>
+
+<li>
+<font color="#009900">is_ex</font>&nbsp; - returns true if an object a
+symbolic expression (i.e.&nbsp; x+y)</li>
+
+<li>
+<font color="#009900">to_double</font>&nbsp; - convert a vpa, ex or string
+to a double value.</li>
+
+<li>
+<font color="#009900">digits</font>&nbsp; - set or view the number of digits
+that newly created vpa object should have</li>
+
+<li>
+<font color="#CC0000">Abs</font>&nbsp; - Absolute value</li>
+
+<li>
+<font color="#CC0000">csgn</font>&nbsp; -</li>
+
+<li>
+<font color="#CC0000">Sqrt</font>&nbsp; - Sqrt(x)&nbsp; => x^(vpa(1)/2)
+or x^(1/vpa(2))</li>
+
+<li>
+<font color="#009900">Cos</font>&nbsp; - the cosine of a sym, vpa , or
+ex variable</li>
+
+<li>
+<font color="#009900">Sin</font> - the sine of a sym, vpa , or ex variable</li>
+
+<li>
+<font color="#009900">Tan</font> - the tangent of a sym, vpa , or ex variable</li>
+
+<li>
+<font color="#009900">aCos</font>&nbsp; - the inverse cosine of a sym,
+vpa , or ex variable</li>
+
+<li>
+<font color="#009900">aSin</font>&nbsp; - the inverse sin of a sym, vpa
+, or ex variable</li>
+
+<li>
+<font color="#009900">aTan</font>&nbsp; - the inverse tangent of a sym,
+vpa , or ex variable</li>
+
+<li>
+<font color="#CC0000">aTan2</font>&nbsp; -</li>
+
+<li>
+<font color="#009900">Cosh</font>&nbsp; - the hyperbolic cosine of a sym,
+vpa , or ex variable</li>
+
+<li>
+<font color="#009900">Sinh</font>&nbsp; - the hyperbolic sine of a sym,
+vpa , or ex variable</li>
+
+<li>
+<font color="#009900">Tanh</font>&nbsp; - the hyperbolic tangent of a sym,
+vpa , or ex variable</li>
+
+<li>
+<font color="#009900">aCosh</font> - the inverse hyperbolic cosine of a
+sym, vpa , or ex variable</li>
+
+<li>
+<font color="#009900">aSinh</font> - the inverse hyperbolic sine of a sym,
+vpa , or ex variable</li>
+
+<li>
+<font color="#009900">aTanh</font>&nbsp; - the inverse hyperbolic tangent
+of a sym, vpa , or ex variable</li>
+
+<li>
+<font color="#009900">Exp</font>&nbsp; - the cosine of a sym, vpa , or
+ex variable</li>
+
+<li>
+<font color="#009900">Log</font>&nbsp; - the cosine of a sym, vpa , or
+ex variable</li>
+
+<li>
+<font color="#CC0000">Zeta</font>&nbsp; -</li>
+
+<li>
+<font color="#CC0000">Tgamma</font>&nbsp; -</li>
+
+<li>
+<font color="#CC0000">Lgamma</font>&nbsp; -</li>
+
+<li>
+<font color="#CC0000">Beta</font>&nbsp; -</li>
+
+<li>
+<font color="#CC0000">Factorial</font>&nbsp; -</li>
+
+<li>
+<font color="#CC0000">Binomial</font>&nbsp; -</li>
+
+<li>
+<font color="#CC0000">Order</font> -</li>
+
+<li>
+<font color="#009900">subs</font> - perform a substitution in an expression</li>
+
+<li>
+<font color="#009900">differentiate</font>&nbsp; - differentiate an expression</li>
+
+<li>
+<font color="#009900">expand</font>&nbsp; -&nbsp; multiply all of the terms
+in an expression out:&nbsp; (x+y)*(x+z) => x^2+x*y+x*z+y*z</li>
+
+<li>
+<font color="#009900">collect</font>&nbsp; - collect similar terms in an
+already expanded expression</li>
+
+<li>
+<font color="#009900">coeff</font>&nbsp; - return the nth coefficient in
+a polynomial</li>
+
+<li>
+<font color="#009900">lcoeff</font>&nbsp; - leading coefficient of a polynomial
+(4x^2+2x+5 => 4)</li>
+
+<li>
+<font color="#009900">tcoeff</font>&nbsp; - trailing coefficient of a polynomial
+(4x^2+2x+5 => 5)</li>
+
+<li>
+<font color="#009900">degree</font>&nbsp; - The degree of a polynomial
+(i.e. x^2+2x+1 => 2)</li>
+
+<li>
+<font color="#009900">ldegree</font>&nbsp; - The low degree of a polynomial
+(i.e. x^2+2x+1&nbsp; => 0)</li>
+
+<li>
+<font color="#009900">quotient</font>&nbsp; -</li>
+
+<li>
+<font color="#009900">remainder</font>&nbsp; -</li>
+
+<li>
+<font color="#009900">premainder</font>&nbsp; -</li>
+
+<li>
+<font color="#CC0000">unit</font>&nbsp; -</li>
+
+<li>
+<font color="#CC0000">content</font>&nbsp; -</li>
+
+<li>
+<font color="#CC0000">primpart</font>&nbsp; -</li>
+
+<li>
+<font color="#CC0000">Gcd</font>&nbsp; - greatest common denominator of
+a polynomial expression</li>
+
+<li>
+<font color="#CC0000">Lcm</font>&nbsp; - least common multiple of a polynomial
+expression</li>
+
+<li>
+<font color="#CC0000">numer</font>&nbsp; -</li>
+
+<li>
+<font color="#CC0000">denom</font>&nbsp; -</li>
+
+<li>
+normal&nbsp; - ?</li>
+
+<li>
+<font color="#CC0000">to_rational</font>&nbsp; -</li>
+
+<li>
+<font color="#CC0000">Series</font>&nbsp; -</li>
+
+<li>
+<font color="#009900">Pi</font>&nbsp; - pi evaluated to the current value
+of digits accuracy.</li>
+
+<li>
+<font color="#009900">splot</font>&nbsp; -plot a symbolic functin over
+a range of values</li>
+
+<li>
+<font color="#CC0000">Saving of expressions, Retrieving of expressions</font></li>
+</ul>
+
+</body>
+</html>
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/main/symbolic/ov-ex.cc	Wed Nov 14 15:09:50 2001 +0000
@@ -0,0 +1,202 @@
+/*
+Copyright (C) 2000 Benjamin Sapp
+
+This is free software; you can redistribute it and/or modify it
+under the terms of the GNU General Public License as published by the
+Free Software Foundation; either version 2, or (at your option) any
+later version.
+
+This is distributed in the hope that it will be useful, but WITHOUT
+ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+for more details.
+
+You can have receive a copy of the GNU General Public License.  Write 
+to the Free Software Foundation, 59 Temple Place - Suite 330, 
+Boston, MA  02111-1307, USA.
+*/
+
+#include <octave/config.h>
+
+#include <cstdlib>
+
+#include <string>
+
+class ostream;
+class octave_sym;
+
+#include <octave/lo-mappers.h>
+#include <octave/lo-utils.h>
+#include <octave/mx-base.h>
+#include <octave/str-vec.h>
+
+#include <octave/defun-dld.h>
+#include <octave/error.h>
+#include <octave/gripes.h>
+#include <octave/oct-obj.h>
+#include <octave/ops.h>
+#include <octave/ov-base.h>
+#include <octave/ov-typeinfo.h>
+#include <octave/ov.h>
+#include <octave/ov-scalar.h>
+#include <octave/pager.h>
+#include <octave/pr-output.h>
+#include <octave/symtab.h>
+#include <octave/variables.h>
+#include <iostream>
+#include <fstream>
+#include "ov-ex.h"
+#include "ov-sym.h"
+#include "ov-vpa.h"
+
+#ifdef DEFUNOP_OP
+#undef DEFUNOP_OP
+#endif
+
+#define DEFUNOP_OP(name, t, op) \
+  UNOPDECL (name, a) \
+  { \
+    CAST_UNOP_ARG (const octave_ ## t&); \
+    return octave_value (new octave_ex (op v.t ## _value ())); \
+  }
+
+DEFUNOP_OP (uminus, ex, -)
+
+DEFNCUNOP_METHOD (incr, ex, increment)
+DEFNCUNOP_METHOD (decr, ex, decrement)
+
+#ifdef DEFBINOP_OP
+#undef DEFBINOP_OP
+#endif
+
+#define DEFBINOP_OP(name, t1, t2, op) \
+  BINOPDECL (name, a1, a2) \
+  { \
+    CAST_BINOP_ARGS (const octave_ ## t1&, const octave_ ## t2&); \
+    return octave_value \
+      (new octave_ex (v1.t1 ## _value () op v2.t2 ## _value ())); \
+  }
+
+#ifdef DEFBINOP_POW
+#undef DEFBINOP_POW
+#endif
+
+#define DEFBINOP_POW(name, t1, t2) \
+  BINOPDECL(name, a1, a2) \
+  { \
+    CAST_BINOP_ARGS (const octave_ ## t1&, const octave_ ## t2&); \
+    return octave_value \
+      (new octave_ex (pow(v1.t1 ## _value (), v2.t2 ## _value ()))); \
+  }
+
+// Addition operations
+DEFBINOP_OP(ex_scalar_add,ex,scalar,+)
+DEFBINOP_OP(scalar_ex_add,scalar,ex,+)
+DEFBINOP_OP(ex_vpa_add,ex,vpa,+)
+DEFBINOP_OP (add, ex, ex, +)
+DEFBINOP_OP(ex_sym_add,ex,sym,+)
+
+// Subtraction operations
+DEFBINOP_OP(ex_scalar_sub,ex,scalar,-)
+DEFBINOP_OP(scalar_ex_sub,scalar,ex,-)
+DEFBINOP_OP(ex_vpa_sub,ex,vpa,-)
+DEFBINOP_OP (sub, ex, ex, -)
+DEFBINOP_OP(ex_sym_sub,ex,sym,-)
+
+// Multiplication operations
+DEFBINOP_OP(ex_scalar_mul,ex,scalar,*)
+DEFBINOP_OP(scalar_ex_mul,scalar,ex,*)
+DEFBINOP_OP(ex_vpa_mul,ex,vpa,*)
+DEFBINOP_OP (mul, ex, ex, *)
+DEFBINOP_OP(ex_sym_mul,ex,sym,*)
+
+// Division operations
+DEFBINOP_OP(ex_scalar_div,ex,scalar,/)
+DEFBINOP_OP(scalar_ex_div,scalar,ex,/)
+DEFBINOP_OP(ex_vpa_div,ex,vpa,/)
+DEFBINOP_OP (div, ex, ex, /)
+DEFBINOP_OP(ex_sym_div,ex,sym,/)
+
+// Power operations 
+DEFBINOP_POW(pow,ex,ex)
+DEFBINOP_POW(ex_scalar_pow,ex,scalar)
+DEFBINOP_POW(scalar_ex_pow,scalar,ex)
+DEFBINOP_POW(ex_vpa_pow,ex,vpa)
+DEFBINOP_POW(ex_sym_pow,ex,sym)
+ 
+void 
+octave_ex::print(ostream& os,bool pr_as_read_syntax) const
+{
+  os << x;
+}
+ 
+octave_ex& octave_ex::operator=(const octave_ex& a)
+{
+  // GiNaC::ex *tmp;
+  // tmp = (a.x.bp->duplicate());
+  // return octave_ex(*tmp);
+  return (*(new octave_ex(a.x)));
+}
+
+void 
+install_ex_type()
+{
+  octave_ex::register_type();
+  
+  cerr << "installing ex type at type-id = " 
+       << octave_ex::static_type_id() << "\n";
+}
+
+void 
+install_ex_ops()
+{
+  INSTALL_UNOP(op_uminus, octave_ex, uminus);             // -x
+  
+  INSTALL_NCUNOP(op_incr, octave_ex, incr);               // x++
+  INSTALL_NCUNOP(op_decr, octave_ex, decr);               // x--
+  
+  // Addition operations
+  INSTALL_BINOP(op_add, octave_scalar, octave_ex, scalar_ex_add);
+  INSTALL_BINOP(op_add, octave_ex, octave_scalar, ex_scalar_add);
+  INSTALL_BINOP(op_add, octave_ex, octave_vpa, ex_vpa_add);
+  INSTALL_BINOP(op_add, octave_ex, octave_ex, add);
+  INSTALL_BINOP(op_add, octave_ex, octave_sym, ex_sym_add);
+  
+  // Subtraction operations
+  INSTALL_BINOP(op_sub, octave_scalar, octave_ex, scalar_ex_sub);
+  INSTALL_BINOP(op_sub, octave_ex, octave_scalar, ex_scalar_sub);
+  INSTALL_BINOP(op_sub, octave_ex, octave_vpa, ex_vpa_sub);
+  INSTALL_BINOP(op_sub, octave_ex, octave_ex, sub);
+  INSTALL_BINOP(op_sub, octave_ex, octave_sym, ex_sym_sub);
+  
+  // Multiplication operations
+  INSTALL_BINOP(op_mul, octave_scalar, octave_ex, scalar_ex_mul);
+  INSTALL_BINOP(op_mul, octave_ex, octave_scalar, ex_scalar_mul);
+  INSTALL_BINOP(op_mul, octave_ex, octave_vpa, ex_vpa_mul);
+  INSTALL_BINOP(op_mul, octave_ex, octave_ex, mul);
+  INSTALL_BINOP(op_mul, octave_ex, octave_sym, ex_sym_mul);
+  
+  // Division operations
+  INSTALL_BINOP(op_div, octave_scalar, octave_ex, scalar_ex_div);
+  INSTALL_BINOP(op_div, octave_ex, octave_scalar, ex_scalar_div);
+  INSTALL_BINOP(op_div, octave_ex, octave_vpa, ex_vpa_div);
+  INSTALL_BINOP(op_div, octave_ex, octave_ex, div);
+  INSTALL_BINOP(op_div, octave_ex, octave_sym, ex_sym_div);
+  
+  // Power operations
+  INSTALL_BINOP(op_pow, octave_scalar, octave_ex, scalar_ex_pow);
+  INSTALL_BINOP(op_pow, octave_ex, octave_scalar, ex_scalar_pow);  
+  INSTALL_BINOP(op_pow, octave_ex, octave_vpa, ex_vpa_pow);        
+  INSTALL_BINOP(op_pow, octave_ex, octave_sym, ex_sym_pow);
+  INSTALL_BINOP(op_pow, octave_ex, octave_ex, pow); 
+}
+
+DEFINE_OCTAVE_ALLOCATOR (octave_ex);
+
+DEFINE_OV_TYPEID_FUNCTIONS_AND_DATA (octave_ex, "ex");
+
+/*
+;;; Local Variables: ***
+;;; mode: C++ ***
+;;; End: ***
+*/
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/main/symbolic/ov-ex.h	Wed Nov 14 15:09:50 2001 +0000
@@ -0,0 +1,100 @@
+/*
+Copyright (C) 2000 Benjamin Sapp
+
+This is free software; you can redistribute it and/or modify it
+under the terms of the GNU General Public License as published by the
+Free Software Foundation; either version 2, or (at your option) any
+later version.
+
+This is distributed in the hope that it will be useful, but WITHOUT
+ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+for more details.
+
+You can have receive a copy of the GNU General Public License.  Write 
+to the Free Software Foundation, 59 Temple Place - Suite 330, 
+Boston, MA  02111-1307, USA.
+*/
+
+#if !defined (octave_ex_h)
+#define octave_ex_h 1
+
+#include <ginac/ginac.h>
+
+void install_ex_type();
+void install_ex_ops();
+
+class 
+octave_ex : public octave_base_value
+{
+public:
+  octave_ex(void):octave_base_value() {}
+
+  octave_ex(octave_ex &ox)
+    {
+      // x = *(ox.x.bp->duplicate());
+      x = ox.x;
+    }
+
+  octave_ex(GiNaC::symbol sym)
+    {
+      // x = *(sym.duplicate());
+      x = sym;
+    }
+  
+  octave_ex(GiNaC::ex expression)
+    {
+      // x = *(expression.bp->duplicate());
+      x = expression;
+    }
+  
+  ~octave_ex() {}
+  
+  octave_ex& operator=(const octave_ex&);
+
+  GiNaC::ex ex_value(bool = false) const
+    {
+      // GiNaC::ex tmp = *(x.bp->duplicate());
+      // return tmp;
+      return x;
+    }
+  
+  octave_value *clone (void) 
+    { 
+      return new octave_ex (*this); 
+    }
+  
+  int rows (void) const { return 1; }
+  int columns (void) const { return 1; }
+  
+  bool is_constant (void) const { return true; }
+  bool is_defined (void) const { return true; }
+
+  bool valid_as_scalar_index(void) const {return false;}
+
+  bool is_true(void) const { return true; }
+   
+  octave_value uminus (void) const { return new octave_ex(-x); }
+
+  void increment (void) { x = x+1;}
+
+  void decrement (void) { x = x-1;}
+  
+  void print(ostream& os,bool pr_as_read_syntax) const;
+  
+private:
+  GiNaC::ex x;
+
+  DECLARE_OCTAVE_ALLOCATOR
+
+  DECLARE_OV_TYPEID_FUNCTIONS_AND_DATA  
+
+};
+
+#endif 
+
+/*
+;;; Local Variables: ***
+;;; mode: C++ ***
+;;; End: ***
+*/
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/main/symbolic/ov-sym.cc	Wed Nov 14 15:09:50 2001 +0000
@@ -0,0 +1,185 @@
+/*
+Copyright (C) 2000 Benjamin Sapp
+
+This is free software; you can redistribute it and/or modify it
+under the terms of the GNU General Public License as published by the
+Free Software Foundation; either version 2, or (at your option) any
+later version.
+
+This is distributed in the hope that it will be useful, but WITHOUT
+ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+for more details.
+
+You can have receive a copy of the GNU General Public License.  Write 
+to the Free Software Foundation, 59 Temple Place - Suite 330, 
+Boston, MA  02111-1307, USA.
+*/
+
+#include <octave/config.h>
+
+#include <cstdlib>
+
+#include <string>
+
+class ostream;
+
+#include <octave/lo-mappers.h>
+#include <octave/lo-utils.h>
+#include <octave/mx-base.h>
+#include <octave/str-vec.h>
+
+#include <octave/error.h>
+#include <octave/gripes.h>
+#include <octave/oct-obj.h>
+#include <octave/ops.h>
+#include <octave/ov-base.h>
+#include <octave/ov-typeinfo.h>
+#include <octave/ov.h>
+#include <octave/ov-scalar.h>
+#include <octave/pager.h>
+#include <octave/pr-output.h>
+#include <octave/symtab.h>
+#include <octave/variables.h>
+#include "ov-ex.h"
+#include "ov-sym.h"
+#include "ov-vpa.h"
+
+#ifdef DEFUNOP_OP
+#undef DEFUNOP_OP
+#endif
+
+#define DEFUNOP_OP(name, t, op) \
+  UNOPDECL (name, a) \
+  { \
+    CAST_UNOP_ARG (const octave_ ## t&); \
+    return octave_value (new octave_ex (op v.t ## _value ())); \
+  }
+
+DEFUNOP_OP (uminus, sym, -)
+
+#ifdef DEFBINOP_OP
+#undef DEFBINOP_OP
+#endif
+
+
+#define DEFBINOP_OP(name, t1, t2, op) \
+  BINOPDECL (name, a1, a2) \
+  { \
+    CAST_BINOP_ARGS (const octave_ ## t1&, const octave_ ## t2&); \
+    return octave_value \
+      (new octave_ex (v1.t1 ## _value () op v2.t2 ## _value ())); \
+  }
+
+#ifdef DEFBINOP_POW
+#undef DEFBINOP_POW
+#endif
+
+#define DEFBINOP_POW(name, t1, t2) \
+  BINOPDECL(name, a1, a2) \
+  { \
+    CAST_BINOP_ARGS (const octave_ ## t1&, const octave_ ## t2&); \
+    return octave_value \
+      (new octave_ex (pow(v1.t1 ## _value (), v2.t2 ## _value ()))); \
+  }
+
+// Addition operations
+DEFBINOP_OP(sym_scalar_add,sym,scalar,+)
+DEFBINOP_OP(scalar_sym_add,scalar,sym,+)
+DEFBINOP_OP(sym_vpa_add,sym,vpa,+)
+DEFBINOP_OP (sym_sym_add, sym, sym, +)
+DEFBINOP_OP(sym_ex_add,sym,ex,+)
+
+// Subtraction operations
+DEFBINOP_OP(sym_scalar_sub,sym,scalar,-)
+DEFBINOP_OP(scalar_sym_sub,scalar,sym,-)
+DEFBINOP_OP(sym_vpa_sub,sym,vpa,-)
+DEFBINOP_OP (sym_sym_sub, sym, sym, -)
+DEFBINOP_OP(sym_ex_sub,sym,ex,-)
+
+// Multiplication operations
+DEFBINOP_OP(sym_scalar_mul,sym,scalar,*)
+DEFBINOP_OP(scalar_sym_mul,scalar,sym,*)
+DEFBINOP_OP(sym_vpa_mul,sym,vpa,*)
+DEFBINOP_OP (sym_sym_mul, sym, sym, *)
+DEFBINOP_OP(sym_ex_mul,sym,ex,*)
+
+// Division operations
+DEFBINOP_OP(sym_scalar_div,sym,scalar,/)
+DEFBINOP_OP(scalar_sym_div,scalar,sym,/)
+DEFBINOP_OP(sym_vpa_div,sym,vpa,/)
+DEFBINOP_OP (sym_sym_div, sym, sym, /)
+DEFBINOP_OP(sym_ex_div,sym,ex,/)
+
+// Power operations 
+DEFBINOP_POW(sym_sym_pow,sym,sym)
+DEFBINOP_POW(sym_scalar_pow,sym,scalar)
+DEFBINOP_POW(scalar_sym_pow,scalar,sym)
+DEFBINOP_POW(sym_vpa_pow,sym,vpa)
+DEFBINOP_POW(sym_ex_pow,sym,ex)
+
+GiNaC::symbol octave_sym::sym_value() const 
+{
+  // This is ugly
+  return ex_to_symbol(GiNaC::ex(*(x.duplicate ())));
+}
+
+void 
+install_sym_type()
+{ 
+  octave_sym::register_type();
+  
+  cerr << "installing sym type at type-id = " 
+       << octave_sym::static_type_id() << "\n";
+}
+
+void
+install_sym_ops()
+{
+  INSTALL_UNOP(op_uminus, octave_sym, uminus);             // -x 
+  
+  // Addition operations
+  INSTALL_BINOP(op_add, octave_scalar, octave_sym, scalar_sym_add);
+  INSTALL_BINOP(op_add, octave_sym, octave_scalar, sym_scalar_add);
+  INSTALL_BINOP(op_add, octave_sym, octave_vpa, sym_vpa_add);
+  INSTALL_BINOP(op_add, octave_sym, octave_sym, sym_sym_add);
+  INSTALL_BINOP(op_add, octave_sym, octave_ex, sym_ex_add);
+  
+  // Subtraction operations
+  INSTALL_BINOP(op_sub, octave_scalar, octave_sym, scalar_sym_sub);
+  INSTALL_BINOP(op_sub, octave_sym, octave_scalar, sym_scalar_sub);
+  INSTALL_BINOP(op_sub, octave_sym, octave_vpa, sym_vpa_sub);
+  INSTALL_BINOP(op_sub, octave_sym, octave_sym, sym_sym_sub);
+  INSTALL_BINOP(op_sub, octave_sym, octave_ex, sym_ex_sub);
+  
+  // Multiplication operations
+  INSTALL_BINOP(op_mul, octave_scalar, octave_sym, scalar_sym_mul);
+  INSTALL_BINOP(op_mul, octave_sym, octave_scalar, sym_scalar_mul);
+  INSTALL_BINOP(op_mul, octave_sym, octave_vpa, sym_vpa_mul);
+  INSTALL_BINOP(op_mul, octave_sym, octave_sym, sym_sym_mul);
+  INSTALL_BINOP(op_mul, octave_sym, octave_ex, sym_ex_mul);
+  
+  // Division operations
+  INSTALL_BINOP(op_div, octave_scalar, octave_sym, scalar_sym_div);
+  INSTALL_BINOP(op_div, octave_sym, octave_scalar, sym_scalar_div);
+  INSTALL_BINOP(op_div, octave_sym, octave_vpa, sym_vpa_div);
+  INSTALL_BINOP(op_div, octave_sym, octave_sym, sym_sym_div);
+  INSTALL_BINOP(op_div, octave_sym, octave_ex, sym_ex_div);
+  
+  // Power operations
+  INSTALL_BINOP(op_pow, octave_scalar, octave_sym, scalar_sym_pow);
+  INSTALL_BINOP(op_pow, octave_sym, octave_scalar, sym_scalar_pow);  
+  INSTALL_BINOP(op_pow, octave_sym, octave_vpa, sym_vpa_pow);        
+  INSTALL_BINOP(op_pow, octave_sym, octave_sym, sym_sym_pow);
+  INSTALL_BINOP(op_pow, octave_sym, octave_ex, sym_ex_pow);
+}  
+
+DEFINE_OCTAVE_ALLOCATOR (octave_sym);
+
+DEFINE_OV_TYPEID_FUNCTIONS_AND_DATA (octave_sym, "sym");
+
+/*
+;;; Local Variables: ***
+;;; mode: C++ ***
+;;; End: ***
+*/
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/main/symbolic/ov-sym.h	Wed Nov 14 15:09:50 2001 +0000
@@ -0,0 +1,92 @@
+/*
+Copyright (C) 2000 Benjamin Sapp
+
+This is free software; you can redistribute it and/or modify it
+under the terms of the GNU General Public License as published by the
+Free Software Foundation; either version 2, or (at your option) any
+later version.
+
+This is distributed in the hope that it will be useful, but WITHOUT
+ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+for more details.
+
+You can have receive a copy of the GNU General Public License.  Write 
+to the Free Software Foundation, 59 Temple Place - Suite 330, 
+Boston, MA  02111-1307, USA.
+*/
+
+#if !defined (octave_sym_h)
+#define octave_sym_h 1
+
+#include <ginac/ginac.h>
+#include "ov.h"
+#include "ov-base.h"
+#include "ov-ex.h"
+
+class Octave_map;
+class octave_value_list;
+class tree_walker;
+
+void install_sym_type();
+void install_sym_ops();
+
+class 
+octave_sym : public octave_base_value
+{
+public:
+  octave_sym(void){}
+
+  octave_sym(char *str)
+  {
+    x = GiNaC::symbol(str);
+  }
+
+  octave_sym(const octave_sym &xtmp):x(xtmp.x){}
+
+  octave_sym(GiNaC::symbol xtmp):x(xtmp){}
+
+  ~octave_sym (void) {}
+
+  octave_value *clone (void) {return new octave_sym(*this);}
+
+  GiNaC::symbol sym_value(void) const;
+
+  octave_value uminus (void){ return (new octave_ex(-x));}
+
+  void print(ostream& os,bool pr_as_read_syntax) const
+  {
+    os << x;
+  }
+
+  int rows (void) const { return 1; }
+  int columns (void) const { return 1; }
+
+  bool is_constant (void) const { return true; }
+  bool is_defined (void) const { return true; }
+  bool is_real_scalar (void) const { return false; }
+  
+  bool is_real_type(void) const {return false;}
+  bool is_scalar_type(void) const {return true;}
+  bool is_numeric_type(void) const {return false;}
+
+  bool valid_as_scalar_index(void) const {return false;}
+
+  bool is_true(void) const { return true; }
+   
+private:
+  GiNaC::symbol x;
+
+  DECLARE_OCTAVE_ALLOCATOR
+
+  DECLARE_OV_TYPEID_FUNCTIONS_AND_DATA  
+
+};
+
+#endif
+
+/*
+;;; Local Variables: ***
+;;; mode: C++ ***
+;;; End: ***
+*/
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/main/symbolic/ov-vpa.cc	Wed Nov 14 15:09:50 2001 +0000
@@ -0,0 +1,234 @@
+/*
+Copyright (C) 2000 Benjamin Sapp
+
+This is free software; you can redistribute it and/or modify it
+under the terms of the GNU General Public License as published by the
+Free Software Foundation; either version 2, or (at your option) any
+later version.
+
+This is distributed in the hope that it will be useful, but WITHOUT
+ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+for more details.
+
+You can have receive a copy of the GNU General Public License.  Write 
+to the Free Software Foundation, 59 Temple Place - Suite 330, 
+Boston, MA  02111-1307, USA.
+*/
+
+
+#include <octave/config.h>
+
+#include <cstdlib>
+
+#include <string>
+
+class ostream;
+
+#include <octave/lo-mappers.h>
+#include <octave/lo-utils.h>
+#include <octave/mx-base.h>
+#include <octave/str-vec.h>
+
+#include <octave/defun-dld.h>
+#include <octave/error.h>
+#include <octave/gripes.h>
+#include <octave/oct-obj.h>
+#include <octave/ops.h>
+#include <octave/ov-base.h>
+#include <octave/ov-typeinfo.h>
+#include <octave/ov.h>
+#include <octave/ov-scalar.h>
+#include <octave/pager.h>
+#include <octave/pr-output.h>
+#include <octave/symtab.h>
+#include <octave/variables.h>
+#include "ov-vpa.h"
+#include "ov-ex.h"
+#include "ov-sym.h"
+
+void
+octave_vpa::print (ostream& os, bool pr_as_read_syntax) const
+{
+  os << scalar;
+}
+
+
+#ifdef DEFUNOP_OP
+#undef DEFUNOP_OP
+#endif
+
+#define DEFUNOP_OP(name, t, op) \
+  UNOPDECL (name, a) \
+  { \
+    CAST_UNOP_ARG (const octave_ ## t&); \
+    return octave_value (new octave_vpa (op v.t ## _value ())); \
+  }
+
+// DEFUNOP_OP (not, vpa, !)
+DEFUNOP_OP (uminus, vpa, -)
+DEFUNOP_OP (transpose, vpa, /* no-op */)
+DEFUNOP_OP (hermitian, vpa, /* no-op */)
+
+DEFNCUNOP_METHOD (incr, vpa, increment)
+DEFNCUNOP_METHOD (decr, vpa, decrement)
+
+#ifdef DEFBINOP_OP
+#undef DEFBINOP_OP
+#endif
+
+#define DEFBINOP_OP(name, t1, t2, op) \
+  BINOPDECL (name, a1, a2) \
+  { \
+    CAST_BINOP_ARGS (const octave_ ## t1&, const octave_ ## t2&); \
+    return octave_value \
+      (new octave_vpa (v1.t1 ## _value () op v2.t2 ## _value ())); \
+  }
+
+#define DEFBINOP_OP_NUM(name, t1, t2, op) \
+  BINOPDECL (name, a1, a2) \
+  { \
+    CAST_BINOP_ARGS (const octave_ ## t1&, const octave_ ## t2&); \
+    return octave_value \
+      (new octave_vpa (v1.t1 ## _value () op v2.t2 ## _value ())); \
+  }
+
+#define DEFBINOP_OP_EX(name, t1, t2, op) \
+  BINOPDECL (name, a1, a2) \
+  { \
+    CAST_BINOP_ARGS (const octave_ ## t1&, const octave_ ## t2&); \
+    return octave_value \
+      (new octave_ex (v1.t1 ## _value () op v2.t2 ## _value ())); \
+  }
+
+
+#ifdef DEFBINOP_POW
+#undef DEFBINOP_POW
+#endif
+
+#define DEFBINOP_POW(name, t1, t2) \
+  BINOPDECL(name, a1, a2) \
+  { \
+    CAST_BINOP_ARGS (const octave_ ## t1&, const octave_ ## t2&); \
+    return octave_value \
+      (new octave_ex (pow(v1.t1 ## _value (), v2.t2 ## _value ()))); \
+  }
+
+// relational ops.
+DEFBINOP_OP (lt, vpa, vpa, <)
+DEFBINOP_OP (le, vpa, vpa, <=)
+DEFBINOP_OP (eq, vpa, vpa, ==)
+DEFBINOP_OP (ge, vpa, vpa, >=)
+DEFBINOP_OP (gt, vpa, vpa, >)
+DEFBINOP_OP (ne, vpa, vpa, !=)
+  //DEFBINOP_OP (el_mul, vpa, vpa, !=)
+
+  //#error The type of return arguements in sym_vpa class are not always correct
+
+// Addition operations
+DEFBINOP_OP_NUM(vpa_scalar_add,vpa,scalar,+)
+DEFBINOP_OP_NUM(scalar_vpa_add,scalar,vpa,+)
+DEFBINOP_OP_NUM (add, vpa, vpa, +)
+DEFBINOP_OP_EX(vpa_sym_add,vpa,sym,+)
+DEFBINOP_OP_EX(vpa_ex_add,vpa,ex,+)
+
+// Subtraction operations
+DEFBINOP_OP_NUM(vpa_scalar_sub,vpa,scalar,-)
+DEFBINOP_OP_NUM(scalar_vpa_sub,scalar,vpa,-)
+DEFBINOP_OP_NUM(sub, vpa, vpa, -)
+DEFBINOP_OP_EX(vpa_sym_sub,vpa,sym,-)
+DEFBINOP_OP_EX(vpa_ex_sub,vpa,ex,-)
+
+// Multiplication operations
+DEFBINOP_OP_NUM(vpa_scalar_mul,vpa,scalar,*)
+DEFBINOP_OP_NUM(scalar_vpa_mul,scalar,vpa,*)
+DEFBINOP_OP_NUM(mul, vpa, vpa, *)
+DEFBINOP_OP_EX(vpa_sym_mul,vpa,sym,*)
+DEFBINOP_OP_EX(vpa_ex_mul,vpa,ex,*)
+
+// Division operations
+DEFBINOP_OP_NUM(vpa_scalar_div,vpa,scalar,/)
+DEFBINOP_OP_NUM(scalar_vpa_div,scalar,vpa,/)
+DEFBINOP_OP_NUM(div, vpa, vpa, /)
+DEFBINOP_OP_EX(vpa_sym_div,vpa,sym,/)
+DEFBINOP_OP_EX(vpa_ex_div,vpa,ex,/)
+
+// Power operations 
+DEFBINOP_POW(pow,vpa,vpa)
+DEFBINOP_POW(vpa_scalar_pow,vpa,scalar)
+DEFBINOP_POW(scalar_vpa_pow,scalar,vpa)
+DEFBINOP_POW(vpa_sym_pow,vpa,sym) 
+DEFBINOP_POW(vpa_ex_pow,vpa,ex)
+
+void 
+install_vpa_type()
+{
+  octave_vpa::register_type ();
+  
+  cerr << "installing vpa type at type-id = "
+       << octave_vpa::static_type_id () << "\n";
+}
+
+void install_vpa_ops()
+{
+  // INSTALL_UNOP (op_not, octave_vpa, not);
+  INSTALL_UNOP (op_uminus, octave_vpa, uminus);
+  INSTALL_UNOP (op_transpose, octave_vpa, transpose);
+  INSTALL_UNOP (op_hermitian, octave_vpa, hermitian);
+  
+  INSTALL_NCUNOP (op_incr, octave_vpa, incr);
+  INSTALL_NCUNOP (op_decr, octave_vpa, decr);
+  
+  // Addition operations
+  INSTALL_BINOP(op_add, octave_scalar, octave_vpa, scalar_vpa_add);
+  INSTALL_BINOP(op_add, octave_vpa, octave_scalar, vpa_scalar_add);
+  INSTALL_BINOP(op_add, octave_vpa, octave_vpa, add);
+  INSTALL_BINOP(op_add, octave_vpa, octave_sym, vpa_sym_add);
+  INSTALL_BINOP(op_add, octave_vpa, octave_ex, vpa_ex_add);
+  
+  // Subtraction operations
+  INSTALL_BINOP(op_sub, octave_scalar, octave_vpa, scalar_vpa_sub);
+  INSTALL_BINOP(op_sub, octave_vpa, octave_scalar, vpa_scalar_sub);
+  INSTALL_BINOP(op_sub, octave_vpa, octave_vpa, sub);
+  INSTALL_BINOP(op_sub, octave_vpa, octave_sym, vpa_sym_sub);
+  INSTALL_BINOP(op_sub, octave_vpa, octave_ex, vpa_ex_sub);
+  
+  // Multiplication operations
+  INSTALL_BINOP(op_mul, octave_scalar, octave_vpa, scalar_vpa_mul);
+  INSTALL_BINOP(op_mul, octave_vpa, octave_scalar, vpa_scalar_mul);
+  INSTALL_BINOP(op_mul, octave_vpa, octave_vpa, mul);
+  INSTALL_BINOP(op_mul, octave_vpa, octave_sym, vpa_sym_mul);
+  INSTALL_BINOP(op_mul, octave_vpa, octave_ex, vpa_ex_mul);
+  
+  // Division operations
+  INSTALL_BINOP(op_div, octave_scalar, octave_vpa, scalar_vpa_div);
+  INSTALL_BINOP(op_div, octave_vpa, octave_scalar, vpa_scalar_div);
+  INSTALL_BINOP(op_div, octave_vpa, octave_vpa, div);
+  INSTALL_BINOP(op_div, octave_vpa, octave_sym, vpa_sym_div);
+  INSTALL_BINOP(op_div, octave_vpa, octave_ex, vpa_ex_div);
+  
+  // Power operations
+  INSTALL_BINOP(op_pow, octave_scalar, octave_vpa, scalar_vpa_pow);
+  INSTALL_BINOP(op_pow, octave_vpa, octave_scalar, vpa_scalar_pow);  
+  INSTALL_BINOP(op_pow, octave_vpa, octave_vpa, pow);        
+  INSTALL_BINOP(op_pow, octave_vpa, octave_sym, vpa_sym_pow);
+  INSTALL_BINOP(op_pow, octave_vpa, octave_ex, vpa_ex_pow);
+  
+  INSTALL_BINOP (op_lt, octave_vpa, octave_vpa, lt);
+  INSTALL_BINOP (op_le, octave_vpa, octave_vpa, le);
+  INSTALL_BINOP (op_eq, octave_vpa, octave_vpa, eq);
+  INSTALL_BINOP (op_ge, octave_vpa, octave_vpa, ge);
+  INSTALL_BINOP (op_gt, octave_vpa, octave_vpa, gt);
+  INSTALL_BINOP (op_ne, octave_vpa, octave_vpa, ne);
+  
+}
+
+DEFINE_OCTAVE_ALLOCATOR (octave_vpa);
+
+DEFINE_OV_TYPEID_FUNCTIONS_AND_DATA (octave_vpa, "vpa");
+
+/*
+;;; Local Variables: ***
+;;; mode: C++ ***
+;;; End: ***
+*/
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/main/symbolic/ov-vpa.h	Wed Nov 14 15:09:50 2001 +0000
@@ -0,0 +1,125 @@
+/*
+Copyright (C) 2000 Benjamin Sapp
+
+This is free software; you can redistribute it and/or modify it
+under the terms of the GNU General Public License as published by the
+Free Software Foundation; either version 2, or (at your option) any
+later version.
+
+This is distributed in the hope that it will be useful, but WITHOUT
+ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+for more details.
+
+You can have receive a copy of the GNU General Public License.  Write 
+to the Free Software Foundation, 59 Temple Place - Suite 330, 
+Boston, MA  02111-1307, USA.
+*/
+
+#if !defined (octave_vpa_h)
+#define octave_vpa_h 1
+
+// GiNaC
+#include <ginac/ginac.h>
+
+class Octave_map;
+class octave_value_list;
+
+class tree_walker;
+
+void install_vpa_type();
+void install_vpa_ops();
+
+// vpa values.
+
+class
+octave_vpa : public octave_base_value
+{
+public:
+
+  octave_vpa (void):octave_base_value()
+    {
+      scalar = GiNaC::numeric(0);
+    }
+  
+  octave_vpa (int i):octave_base_value()
+    { 
+      scalar = GiNaC::numeric(0);
+    }
+  
+  octave_vpa (const octave_vpa& s):octave_base_value()
+    { 
+      scalar = s.scalar;
+    }
+  
+  octave_vpa (const GiNaC::numeric& s):octave_base_value()
+    {
+      scalar = s;
+    }
+  
+  octave_vpa( const GiNaC::ex& x):octave_base_value()
+    {
+      scalar = GiNaC::ex_to_numeric(x);
+    }
+
+  ~octave_vpa (void) { }
+
+  octave_value *clone (void) { return new octave_vpa (*this); }
+
+#if 0
+  void *operator new (size_t size);
+  void operator delete (void *p, size_t size);
+#endif 
+
+  int rows (void) const { return 1; }
+  int columns (void) const { return 1; }
+
+  bool is_constant (void) const { return true; }
+
+  bool is_defined (void) const { return true; }
+  bool is_real_scalar (void) const { return true; }
+
+  octave_value all (void) const { return (double) (scalar != 0); }
+  octave_value any (void) const { return (double) (scalar != 0); }
+
+  bool is_real_type (void) const { return true; }
+  bool is_scalar_type (void) const { return true; }
+  bool is_vpa_type (void) const { return true; }
+
+  bool valid_as_scalar_index (void) const
+    { return scalar == 1; }
+
+  bool valid_as_zero_index (void) const
+    { return scalar == 0; }
+
+  bool is_true (void) const { return (scalar != 0); }
+
+  double double_value (bool = false) const { return scalar.to_double(); }
+
+  GiNaC::numeric vpa_value (bool = false) const { return scalar; }
+
+  octave_value hermitian (void) const { return new octave_vpa (scalar); }
+
+  void increment (void) { ++scalar; }
+
+  void decrement (void) { --scalar; }
+
+  void print (ostream& os, bool pr_as_read_syntax = false) const;
+
+private:
+  
+  GiNaC::numeric scalar;
+
+  DECLARE_OCTAVE_ALLOCATOR
+
+  DECLARE_OV_TYPEID_FUNCTIONS_AND_DATA
+};
+
+#endif
+
+/*
+;;; Local Variables: ***
+;;; mode: C++ ***
+;;; End: ***
+*/
+
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/main/symbolic/splot.m	Wed Nov 14 15:09:50 2001 +0000
@@ -0,0 +1,17 @@
+## -*- texinfo -*-
+## @deftypefn {Function File} splot(@var{f},@var{x},@var{range})
+## Plot a symbolic function f(x) over range.
+## @end deftypefn
+
+function splot(expression,symbol,range)
+  ## we should be a little smarter about this
+  t = linspace(min(range),max(range),400);
+  x = zeros(size(t));
+  j = 1;
+  for i = t
+    x(j) = to_double(subs(expression,symbol,vpa(t(j))));
+    j++;
+  endfor
+
+  plot(t,x);
+endfunction
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/main/symbolic/symbols.cc	Wed Nov 14 15:09:50 2001 +0000
@@ -0,0 +1,563 @@
+
+// 2001-09-18 Paul Kienzle <pkienzle@users.sf.net>
+// * use GiNaC::is_a<GiNaC::blah>(x) rather than is_ex_of_type(x, blah)
+// * use GiNaC::ex_to<GiNaC::blah>(x) rather than ex_to_blah(x)
+
+#include <octave/config.h>
+#include <cstdlib>
+
+#include <string>
+
+class ostream;
+class octave_sym;
+
+#include <octave/lo-mappers.h>
+#include <octave/lo-utils.h>
+#include <octave/mx-base.h>
+#include <octave/str-vec.h>
+
+#include <octave/defun-dld.h>
+#include <octave/error.h>
+#include <octave/gripes.h>
+#include <octave/oct-obj.h>
+#include <octave/ops.h>
+#include <octave/ov-base.h>
+#include <octave/ov-typeinfo.h>
+#include <octave/ov.h>
+#include <octave/ov-scalar.h>
+#include <octave/pager.h>
+#include <octave/pr-output.h>
+#include <octave/symtab.h>
+#include <octave/variables.h>
+#include <iostream>
+#include <fstream>
+
+#include <ginac/ginac.h>
+
+#include "ov-vpa.h"
+#include "ov-ex.h"
+#include "ov-sym.h"
+#include "symbols.h"
+
+bool get_expression(const octave_value arg, GiNaC::ex& expression)
+{
+  const octave_value& rep = (arg).get_rep();
+  
+  if (arg.type_id () == octave_vpa::static_type_id ())
+    {
+      GiNaC::numeric x = ((octave_vpa& ) rep).vpa_value();
+      expression = x+0;
+    }
+  else if (arg.type_id () == octave_sym::static_type_id ())
+    {
+      GiNaC::symbol x = ((octave_sym& ) rep).sym_value();
+      expression = x+0;
+    }
+  else if (arg.type_id () == octave_ex::static_type_id ())
+    {
+      GiNaC::ex x = ((octave_ex& ) rep).ex_value();
+      expression = x;
+    }
+  else if (arg.is_real_scalar ())
+    {
+      GiNaC::numeric x(arg.double_value ());
+      expression = x+0;
+    }
+  else 
+    {
+      return false;
+    }
+
+  return true;
+}
+
+bool get_symbol(const octave_value arg, GiNaC::symbol& sym)
+{
+  const octave_value& rep = arg.get_rep ();
+     
+  if (arg.type_id () == octave_sym::static_type_id ())
+    sym = ((octave_sym& ) rep).sym_value();
+  else if (arg.type_id () == octave_ex::static_type_id ())
+    {
+      GiNaC::ex x = ((octave_ex& ) rep).ex_value();
+      if(GiNaC::is_a<GiNaC::symbol>(x))
+	sym = GiNaC::ex_to<GiNaC::symbol>(x);
+      else
+	return false;
+    }
+  else
+    return false;
+
+  return true; 
+}
+
+bool get_numeric(const octave_value arg, GiNaC::numeric& number)
+{
+  const octave_value& rep = arg.get_rep ();
+
+  if (arg.type_id () == octave_ex::static_type_id ())
+    {
+      GiNaC::ex x = ((octave_ex& ) rep).ex_value();
+      if(GiNaC::is_a<GiNaC::numeric>(x))
+	number = GiNaC::ex_to<GiNaC::numeric>(x);
+      else
+	return false;
+    }
+  else if (arg.type_id () == octave_vpa::static_type_id ())
+    number = ((const octave_vpa &) rep).vpa_value ();
+  else if (arg.is_real_scalar ())
+    number = GiNaC::numeric (arg.double_value ());
+  else if (arg.is_string ())
+    number = GiNaC::numeric (arg.string_value ().c_str ());
+  else
+    return false;
+
+  return true;
+}
+
+DEFUN_DLD(symbols,args,,"Initialize symbolic manipulation")
+{
+  octave_value retval;
+  install_ex_type();
+  install_sym_type();
+  install_vpa_type();
+  install_ex_ops();
+  install_sym_ops();
+  install_vpa_ops();
+  return retval;
+}
+
+DEFUN_DLD (vpa, args, ,
+"-*- texinfo -*-\n\
+@deftypefn {Loadable Function} {n =} vpa(@var{s})\n\
+\n\
+Creates a variable precision arithmetic variable from @var{s}.\n\
+@var{s} can be a scalar, vpa value, string or a ex value that \n\
+is a number.\n\
+@end deftypefn\n\
+")
+{
+  octave_value retval;
+  GiNaC::numeric d;
+  int nargin = args.length();
+  
+  if (nargin == 1)
+    {
+      if (!get_numeric (args(0), d))
+	{
+	  gripe_wrong_type_arg ("vpa", args(0));
+	  return retval;
+	} 
+    }
+  else
+    {
+      print_usage("vpa");
+      return retval;
+    }
+
+  retval = octave_value(new octave_vpa(d));
+
+  return retval;
+}
+
+DEFUN_DLD(to_double,args, , 
+"-*- texinfo -*-\n\
+@deftypefn {Loadable Function} {d =} to_double(@var{n})\n\
+\n\
+Convert a vpa, string, ex or string type to a double.\n\
+\n\
+@end deftypefn\n\
+")
+{
+  octave_value retval;
+  int nargin = args.length();
+  GiNaC::numeric num;
+
+  if (nargin != 1)
+    {
+      print_usage("to_double");
+      return retval;
+    }
+
+  if (!get_numeric (args(0), num))
+    {
+      print_usage("to_double");
+      return retval;
+    }
+
+  retval = octave_value(num.to_double ());
+
+  return retval;
+}
+
+DEFUN_DLD(digits, args, , 
+"-*- texinfo -*-\n\
+@deftypefn {Loadable Function} {@var{dgts} =} digits([@var{num}])\n\
+Change the precision for the vpa type
+@end deftypefn\n\
+")
+{
+  octave_value retval;
+  int nargin = args.length();
+ 
+  if ((nargin != 1) && (nargin != 0))
+    {
+      error("you must supply 0 or 1 arguments\n");
+      return(retval);
+    }
+  
+  if(nargin == 1)
+    {
+      if(args(0).is_real_scalar())
+	{
+	  GiNaC::Digits = int(args(0).double_value());
+	}
+      else
+	{
+	  print_usage("digits");
+	}
+    }
+
+  double dig = double(GiNaC::Digits);
+  retval = octave_value(dig);
+  return(retval);
+}
+
+DEFUN_DLD(Pi,args, ,
+"-*- texinfo -*-\n\
+Pi evaluated to the current value of Digits\n\
+\n\
+@seealso{digits}")
+{
+  return octave_value(new octave_vpa(GiNaC::ex_to_numeric(GiNaC::Pi.evalf())));
+}
+
+DEFUN_DLD(is_vpa, args, ,
+"Return true if an object is of type vpa, false otherwise.\n")
+{
+  bool retval;
+  retval = (args(0).type_id() == octave_vpa::static_type_id());
+  return octave_value(retval);
+}
+
+DEFUN_DLD (sym,args, , 
+"-*- texinfo -*-\n\
+Create an object of type symbol\n")
+{
+  int nargin = args.length ();
+
+  if (nargin != 1)
+    {
+      error("one argument expected\n");
+      return octave_value ();
+    }
+
+  GiNaC::symbol xtmp(args(0).string_value());
+  octave_sym x(xtmp);
+  return octave_value(new octave_sym(x));
+}
+
+DEFUN_DLD(is_sym,args, ,"Return true if an object is of type sym false otherwise.\n")
+{
+  bool retval;
+  retval = (args(0).type_id() == octave_sym::static_type_id());
+  return octave_value(retval);
+}
+
+DEFUN_DLD(differentiate,args,,
+"-*- texinfo -*-\n\
+@deftypefn Loadable Function {da_dx =} differentiate(@var{a},@var{x} [, @var{n}])\n\
+\n\
+Return the @var{n}th derivative of @var{a} with respect to @var{x}. If @var{n} is not\n\
+supplied then a default value of 1 is used.\n\
+@end deftypefn")
+{
+  GiNaC::ex expression;
+  GiNaC::symbol variable;
+  GiNaC::numeric num;
+  int order;
+  octave_value retval;
+  int nargin = args.length();
+
+  if ((nargin < 2) || (nargin > 3))
+    {
+      print_usage ("differentiate");
+      return retval;
+    }
+ 
+  if (!get_expression (args(0), expression))
+    {
+      print_usage ("differentiate");
+      return retval;
+    }
+
+  if (!get_symbol (args(1), variable))
+    {
+      print_usage ("differentiate");
+      return retval;
+    }
+
+  if (nargin == 3)
+    {
+      if (!get_numeric (args(2), num))
+	{
+	  print_usage ("differentiate");
+	  return retval;
+	}
+      order = int(num.to_double ());
+      if (order < 0)
+	{
+	  error("must supply an integer greater than zero\n");
+	  return retval;
+	}
+    }
+  else
+    order = 1;
+
+  return octave_value(new octave_ex(expression.diff(variable,order)));
+}
+
+DEFINE_EX_GINAC_FUNCTION(Cos,cos,"cosine");
+DEFINE_EX_GINAC_FUNCTION(Sin,sin,"sine");
+DEFINE_EX_GINAC_FUNCTION(Tan,tan,"tangent");
+DEFINE_EX_GINAC_FUNCTION(aCos,acos,"inverse cosine");
+DEFINE_EX_GINAC_FUNCTION(aSin,asin,"inverse sine");
+DEFINE_EX_GINAC_FUNCTION(aTan,atan,"inverse tangent");
+DEFINE_EX_GINAC_FUNCTION(Cosh,cosh,"hyperbolic cosine");
+DEFINE_EX_GINAC_FUNCTION(Sinh,sinh,"hyperbolic sine");
+DEFINE_EX_GINAC_FUNCTION(Tanh,tanh,"hyperbolic tangent");
+DEFINE_EX_GINAC_FUNCTION(aCosh,acosh,"inverse hyperbolic cosine");
+DEFINE_EX_GINAC_FUNCTION(aSinh,asinh,"inverse hyperbolic sine");
+DEFINE_EX_GINAC_FUNCTION(aTanh,atanh,"inverse hyperbolic tangent");
+DEFINE_EX_GINAC_FUNCTION(Exp,exp,"exponential");
+DEFINE_EX_GINAC_FUNCTION(Log,log,"logarithm");
+DEFINE_EX_GINAC_FUNCTION(Abs,abs,"absolute value");
+
+DEFINE_EX_SYM_GINAC_FUNCTION(degree, degree,"degree");
+DEFINE_EX_SYM_GINAC_FUNCTION(ldegree, ldegree,"low degree");
+DEFINE_EX_SYM_GINAC_FUNCTION(tcoeff, tcoeff, "trailing coeffiecient");
+DEFINE_EX_SYM_GINAC_FUNCTION(lcoeff, lcoeff, "leading coefficient");
+
+DEFINE_EX_EX_SYM_GINAC_FUNCTION(quotient,quo,"quotient");
+DEFINE_EX_EX_SYM_GINAC_FUNCTION(remainder,rem,"remainder");
+DEFINE_EX_EX_SYM_GINAC_FUNCTION(premainder,prem,"pseudo-remainder");
+
+DEFUN_DLD(is_ex,args,,
+"-*- texinfo -*-\n\
+@deftypefn Loadable Function {bool =} is_ex(@var{a})\n\
+\n\
+Return true if an object is of type ex.\n\
+@seealso{is_sym, is_vpa}")
+{
+  bool retval;
+  retval = (args(0).type_id() == octave_ex::static_type_id());
+  return octave_value(retval);
+}
+
+DEFUN_DLD(subs,args,,
+"-*- texinfo -*-\n\
+@deftypefn Loadable Function {b =} subs(@var{a},@var{x},@var{n})\n\
+\n\
+Substitute a number for a variables in an expression\n\
+@table @var\n\
+@item a\n\
+ The expresion in which the substition will occur.\n\
+@item x\n\
+ The variable that will be substituted.\n\
+@item n\n\
+ The expression,vpa value or scalar that will replace x.\n\
+@end table\n\
+\n\
+@end deftypefn\n\
+")
+{
+  GiNaC::ex expression;
+  GiNaC::symbol the_sym;
+  GiNaC::ex ex_sub;
+  GiNaC::ex tmp;
+  int nargin = args.length ();
+  octave_value retval;
+
+  if (nargin != 3)
+    {
+      error("need three arguments\n");
+      return retval;
+    }
+
+  try 
+    {
+      if (!get_expression (args(0), expression))
+	{
+	  gripe_wrong_type_arg ("subs",args(0));
+	  return retval;
+	}
+
+      if (!get_symbol (args(1), the_sym))
+	{
+	  gripe_wrong_type_arg("subs",args(1));
+	  return retval;
+	}
+
+      if (!get_expression (args(2), ex_sub))
+	{
+	  gripe_wrong_type_arg ("subs",args(2));
+	  return retval;
+	}
+
+      tmp = expression.subs(the_sym == ex_sub);
+      retval = octave_value (new octave_ex(tmp));
+    }
+  catch (exception e)
+    {
+      e.what ();
+      return octave_value ();
+    }
+
+  return retval;
+}
+
+DEFUN_DLD(expand,args,,
+"-*- texinfo -*-\n\
+@deftypefn Loadable Function {b =} expand(@var{a})\n\
+\n\
+Expand an expression\n\
+@table @var\n\
+@item a\n\
+ The expresion in which the expansion will occur.\n\
+@end table\n\
+\n\
+@end deftypefn\n\
+")
+{
+  GiNaC::ex expression;
+  GiNaC::symbol the_sym;
+  GiNaC::ex result;
+  octave_value retval;
+
+  if(args.length() != 1)
+    {
+      print_usage("expand");
+      return retval;
+    }
+  if(args(0).type_id() == octave_ex::static_type_id())
+    {
+      const octave_value& rep1 = args(0).get_rep();
+      expression = ((const octave_ex& ) rep1).ex_value();
+    }
+  else
+    {
+      gripe_wrong_type_arg("expand",args(0));
+    }
+
+  result = expression.expand();
+  return octave_value(new octave_ex(result));
+}
+
+DEFUN_DLD(coeff,args,,
+"-*- texinfo -*-
+@deftypefn {Loadable Function} {b =} coeff(@var{a},@var{x},@var{n})\n\
+\n\
+Obtain the @var{n}th coefficient of the variable @var{x} in @var{a}.  
+\n\
+@end deftypefn\n\
+")
+{
+  octave_value retval;
+  GiNaC::ex expression;
+  GiNaC::symbol sym;
+  int n;
+
+  if(args.length () != 3)
+    {
+      print_usage("coeff");
+      return retval;
+    }
+
+  if(args(0).type_id() == octave_ex::static_type_id())
+    {
+      const octave_value& rep0 = args(0).get_rep();
+      expression = ((const octave_ex& ) rep0).ex_value();
+    }
+  else
+    {
+      gripe_wrong_type_arg("coeff",args(0));
+      return retval;
+    }
+
+  if(args(1).type_id() == octave_sym::static_type_id())
+    {
+      const octave_value& rep1 = args(1).get_rep();
+      sym = ((const octave_sym& ) rep1).sym_value();
+    }
+  else
+    {
+      gripe_wrong_type_arg("coeff",args(1));
+      return retval;
+    }
+
+  if(args(2).is_real_scalar())
+    {
+      n = (int )args(2).double_value();
+    }
+  else
+    {
+      gripe_wrong_type_arg("coeff",args(2));
+      return retval;
+    }
+
+  retval = octave_value (new octave_ex (expression.coeff(sym,n)));
+
+  return retval;
+}
+
+DEFUN_DLD(collect,args,,
+"-*- texinfo -*-\n\
+@deftypefn Loadable Function {b =} collect(@var{a},@var{x})\n\
+\n\
+collect the terms in @var{a} as a univariate polynomial in @var{x}\n\
+@table @var\n\
+@item a\n\
+ The expresion in which the collection will occur.\n\
+@item x\n\
+ The variable that will be collected.\n\
+@end table\n\
+\n\
+@end deftypefn\n\
+")
+{
+  octave_value retval;
+  GiNaC::ex expression;
+  GiNaC::symbol the_sym;
+
+  if(args.length() != 2)
+    {
+      print_usage("collect");
+      return retval;
+    }
+
+  if(args(0).type_id() == octave_ex::static_type_id())
+    {
+      const octave_value& rep1 = args(0).get_rep();
+      expression = ((const octave_ex& ) rep1).ex_value();
+    }
+  else
+    {
+      gripe_wrong_type_arg("collect",args(0));
+    }
+
+  if(args(1).type_id() == octave_sym::static_type_id())
+    {
+      const octave_value& rep2 = args(1).get_rep();
+      the_sym = ((octave_sym& ) rep2).sym_value();
+    }
+  else
+    {
+      gripe_wrong_type_arg("collect",args(1));
+    }
+
+  retval = new octave_ex(expression.collect(the_sym));
+
+  return retval;
+}
+
+
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/main/symbolic/symbols.h	Wed Nov 14 15:09:50 2001 +0000
@@ -0,0 +1,133 @@
+
+bool get_expression(const octave_value arg, GiNaC::ex& expression);
+bool get_symbol(const octave_value arg, GiNaC::symbol& sym);
+bool get_numeric(const octave_value arg, GiNaC::numeric& number);
+
+#define DEFINE_EX_GINAC_FUNCTION(oct_name,ginac_name,description) \
+DEFUN_DLD(oct_name, args, , \
+"-*- texinfo -*-\n\
+@deftypefn Loadable Function {r =}" # oct_name "(@var{x})\n\
+Return the " description " of a symbolic expression.\n\
+@end deftypefn\n\
+") \
+{ \
+  int nargin = args.length (); \
+  octave_value retval; \
+  octave_ex *r = NULL; \
+  GiNaC::ex expression; \
+ \
+  if (nargin != 1) \
+    { \
+      print_usage(# oct_name); \
+      return retval; \
+    } \
+ \
+  try \
+   { \
+      if(!get_expression(args(0), expression)) \
+        { \
+          print_usage(# oct_name); \
+          return retval; \
+        } \
+ \
+      r = new octave_ex(GiNaC::ginac_name (expression)); \
+ \
+    } \
+  catch (exception e) \
+    { \
+      e.what (); \
+      return octave_value (); \
+    } \
+ \
+  return octave_value(r); \
+}
+
+#define DEFINE_EX_SYM_GINAC_FUNCTION(oct_name,ginac_name,description) \
+DEFUN_DLD(oct_name, args, , \
+"-*- texinfo -*-\n\
+@deftypefn Loadable Function {r =}" # oct_name "(@var{a}, @var{x})\n\
+Return the " description " of a symbolic expression.\n\
+@end deftypefn\n\
+") \
+{ \
+  int nargin = args.length (); \
+  octave_value retval; \
+  octave_ex *r = NULL; \
+  GiNaC::ex expression; \
+  GiNaC::symbol sym; \
+ \
+  if (nargin != 2) \
+    { \
+      error("need exactly two arguments"); \
+      return retval; \
+    } \
+ \
+  if(!get_expression(args(0), expression)) \
+    { \
+      print_usage(# oct_name); \
+      return retval; \
+    } \
+ \
+  if (!get_symbol(args(1), sym)) \
+    { \
+      print_usage(# oct_name); \
+      return retval; \
+    } \
+ \
+  r = new octave_ex(expression.ginac_name(sym)); \
+ \
+  return octave_value(r); \
+}
+
+#define DEFINE_EX_EX_SYM_GINAC_FUNCTION(oct_name,ginac_name,description) \
+DEFUN_DLD(oct_name, args, , \
+"-*- texinfo -*-\n\
+@deftypefn Loadable Function {r =}" # oct_name "(@var{a}, @var{x})\n\
+Return the " description " of a symbolic expression.\n\
+@end deftypefn\n\
+") \
+{ \
+  int nargin = args.length (); \
+  octave_value retval; \
+  octave_ex *r = NULL; \
+  GiNaC::ex expression0; \
+  GiNaC::ex expression1; \
+  GiNaC::symbol sym; \
+ \
+  if (nargin != 3) \
+    { \
+      error("need exactly three arguments"); \
+      return retval; \
+    } \
+ \
+  if(!get_expression(args(0), expression0)) \
+    { \
+      gripe_wrong_type_arg(# oct_name, args(0)); \
+      print_usage(# oct_name); \
+      return retval; \
+    } \
+ \
+  if(!get_expression(args(1), expression1)) \
+    { \
+      gripe_wrong_type_arg(# oct_name, args(1)); \
+      print_usage(# oct_name); \
+      return retval; \
+    } \
+ \
+  if (!get_symbol(args(2), sym)) \
+    { \
+      gripe_wrong_type_arg(# oct_name, args(2)); \
+      print_usage(# oct_name); \
+      return retval; \
+    } \
+ \
+  r = new octave_ex(ginac_name (expression0, expression1, sym)); \
+ \
+  return octave_value(r); \
+}
+
+/*
+;;; Local Variables: ***
+;;; mode: C++ ***
+;;; End: ***
+*/