#ifndef RPNFUNC_H
#define RPNFUNC_H


#include <deque>
using namespace std;

#include <rpn.h>


class rpnprogset: public rpnfunction
{
public:

  rpnprogset() {}
  rpnprogset(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpnprogset() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpninteger& n);
  void visit(deque<rpnbase*>& ds,rpnprogram& p);

  string const name() const { return string("p@"); }

  void eval( deque<rpnbase*>& ds );
};

class rpnpush : public rpnfunction
{
public:

  rpnpush() {}
  rpnpush(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpnpush() {}
  rpnbase* copy() const;

  string const name() const { return string("push"); }

  void eval( deque<rpnbase*>& ds );
};

class rpnpop : public rpnfunction
{
public:

  rpnpop() {}
  rpnpop(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpnpop() {}
  rpnbase* copy() const;

  string const name() const { return string("pop"); }

  void eval( deque<rpnbase*>& ds );
};

class rpnpushn : public rpnfunction
{
public:

  rpnpushn() {}
  rpnpushn(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpnpushn() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpninteger& n);

  string const name() const { return string("pushn"); }

  void eval( deque<rpnbase*>& ds );
};

class rpnpopn : public rpnfunction
{
public:

  rpnpopn() {}
  rpnpopn(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpnpopn() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpninteger& n);

  string const name() const { return string("popn"); }

  void eval( deque<rpnbase*>& ds );
};

class dssize2 : public rpnfunction
{
public:

  dssize2() {}
  dssize2(deque<rpnbase*>& ds, bool const evaluate=true);
  ~dssize2() {}
  rpnbase* copy() const;

  string const name() const { return string("size2"); }

  void eval( deque<rpnbase*>& ds );
};

class rpneval : public rpnfunction
{
public:

  rpneval() {}
  rpneval(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpneval() {}
  rpnbase* copy() const;

  string const name() const { return string("eval"); }

  void eval( deque<rpnbase*>& ds );
};

class rpnclear : public rpnfunction
{
public:

  rpnclear() {}
  rpnclear(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpnclear() {}
  rpnbase* copy() const;

  string const name() const { return string("clear"); }

  void eval( deque<rpnbase*>& ds );
};

class rpnclearvar : public rpnfunction
{
public:

  rpnclearvar() {}
  rpnclearvar(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpnclearvar() {}
  rpnbase* copy() const;

  string const name() const { return string("clearvar"); }

  void eval( deque<rpnbase*>& ds );
};

class rpnclearboth : public rpnfunction
{
public:

  rpnclearboth() {}
  rpnclearboth(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpnclearboth() {}
  rpnbase* copy() const;

  string const name() const { return string("clearboth"); }

  void eval( deque<rpnbase*>& ds );
};

class rpndup : public rpnfunction
{
public:

  rpndup() {}
  rpndup(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpndup() {}
  rpnbase* copy() const;

  string const name() const { return string("dup"); }

  void eval( deque<rpnbase*>& ds );
};

class rpndupn : public rpnfunction
{
public:

  rpndupn() {}
  rpndupn(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpndupn() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpninteger& n);

  string const name() const { return string("dupn"); }

  void eval( deque<rpnbase*>& ds );
};

class dssize : public rpnfunction
{
public:

  dssize() {}
  dssize(deque<rpnbase*>& ds, bool const evaluate=true);
  ~dssize() {}
  rpnbase* copy() const;

  string const name() const { return string("size"); }

  void eval( deque<rpnbase*>& ds );
};

class rev : public rpnfunction
{
public:

  rev() {}
  rev(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rev() {}
  rpnbase* copy() const;

  string const name() const { return string("rev"); }

  void eval( deque<rpnbase*>& ds );
};

class rot : public rpnfunction
{
public:

  rot() {}
  rot(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rot() {}
  rpnbase* copy() const;

  string const name() const { return string("rot"); }

  void eval( deque<rpnbase*>& ds );
};

class rotn : public rpnfunction
{
public:

  rotn() {}
  rotn(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rotn() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpninteger& n);

  string const name() const { return string("rotn"); }

  void eval( deque<rpnbase*>& ds );
};

class rpnswap: public rpnfunction
{
public:

  rpnswap() {}
  rpnswap(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpnswap() {}
  rpnbase* copy() const;

  string const name() const { return string("swap"); }

  void eval( deque<rpnbase*>& ds );
};


class rpnswap2: public rpnfunction
{
public:

  rpnswap2() {}
  rpnswap2(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpnswap2() {}
  rpnbase* copy() const;

  string const name() const { return string("|"); }

  void eval( deque<rpnbase*>& ds );
};


class dropi: public rpnfunction
{
public:

  dropi() {}
  dropi(deque<rpnbase*>& ds, bool const evaluate=true);
  ~dropi() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpninteger& n);

  string const name() const { return string("\\i"); }

  void eval( deque<rpnbase*>& ds );
};

class drop: public rpnfunction
{
public:

  drop() {}
  drop(deque<rpnbase*>& ds, bool const evaluate=true);
  ~drop() {}
  rpnbase* copy() const;

  string const name() const { return string("drop"); }

  void eval( deque<rpnbase*>& ds );
};




// Identical class to drop. Added for symbolic drop "\" .
class dropsymb: public drop 
{
public:

  dropsymb() {}
  dropsymb(deque<rpnbase*>& ds, bool const evaluate=true);
  ~dropsymb() {}

  string const name() const { return string("\\"); }

};

class dropn: public rpnfunction
{
public:

  dropn() {}
  dropn(deque<rpnbase*>& ds, bool const evaluate=true);
  ~dropn() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpninteger& n);

  string const name() const { return string("dropn"); }

  void eval( deque<rpnbase*>& ds );
};

class ifthen : public rpnfunction
{
public:

  ifthen() {}
  ifthen(deque<rpnbase*>& ds, bool const evaluate=true);
  ~ifthen() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpnreal& n);
  void visit(deque<rpnbase*>& ds,rpninteger& n);

  string const name() const { return string("ifthen"); }

  void eval( deque<rpnbase*>& ds );
}; 

class thenif : public rpnfunction
{
public:

  thenif() {}
  thenif(deque<rpnbase*>& ds, bool const evaluate=true);
  ~thenif() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpnreal& n);
  void visit(deque<rpnbase*>& ds,rpninteger& n);

  string const name() const { return string("thenif"); }

  void eval( deque<rpnbase*>& ds );
}; 

class ifthenelse : public rpnfunction
{
public:

  ifthenelse() {}
  ifthenelse(deque<rpnbase*>& ds, bool const evaluate=true);
  ~ifthenelse() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpnreal& n);
  void visit(deque<rpnbase*>& ds,rpninteger& n);

  string const name() const { return string("ifthenelse"); }

  void eval( deque<rpnbase*>& ds );
};

class thenelseif : public rpnfunction
{
public:

  thenelseif() {}
  thenelseif(deque<rpnbase*>& ds, bool const evaluate=true);
  ~thenelseif() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpnreal& n);
  void visit(deque<rpnbase*>& ds,rpninteger& n);

  string const name() const { return string("thenelseif"); }

  void eval( deque<rpnbase*>& ds );
};

class var: public rpnfunction
{
public:

  var() {}
  var(deque<rpnbase*>& ds, bool const evaluate=true);
  ~var() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpnstring& n);

  string const name() const { return string("var"); }

  void eval( deque<rpnbase*>& ds );
};

class vardel: public rpnfunction
{
public:

  vardel() {}
  vardel(deque<rpnbase*>& ds, bool const evaluate=true);
  ~vardel() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpnstring& n);

  string const name() const { return string("rm"); }

  void eval( deque<rpnbase*>& ds );
};

class vareval: public rpnfunction
{
public:

  vareval() {}
  vareval(deque<rpnbase*>& ds, bool const evaluate=true);
  ~vareval() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpnstring& n);
  void visit(deque<rpnbase*>& ds,rpninteger& n);
  void visit(deque<rpnbase*>& ds,rpnprogram& p);

  string const name() const { return string("&"); }

  void eval( deque<rpnbase*>& ds );
};

class varpushd: public rpnfunction
{
public:

  varpushd() {}
  varpushd(deque<rpnbase*>& ds, bool const evaluate=true);
  ~varpushd() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpnstring& s);
  void visit(deque<rpnbase*>& ds,rpnprogram& p);

  string const name() const { return string("pushd"); }

  void eval( deque<rpnbase*>& ds );
};

class varpopd: public rpnfunction
{
public:

  varpopd() {}
  varpopd(deque<rpnbase*>& ds, bool const evaluate=true);
  ~varpopd() {}
  rpnbase* copy() const;

  string const name() const { return string("popd"); }

  void eval( deque<rpnbase*>& ds );
};


class depthd: public rpnfunction
{
public:

  depthd() {}
  depthd(deque<rpnbase*>& ds, bool const evaluate=true);
  ~depthd() {}
  rpnbase* copy() const;

  string const name() const { return string("depthd"); }

  void eval( deque<rpnbase*>& ds );
};



class varls: public rpnfunction
{
public:

  varls() {}
  varls(deque<rpnbase*>& ds, bool const evaluate=true);
  ~varls() {}
  rpnbase* copy() const;

  string const name() const { return string("ls"); }

  void eval( deque<rpnbase*>& ds );
};

class vartree : public rpnfunction
{
public:

  vartree() {}
  vartree(deque<rpnbase*>& ds, bool const evaluate=true);
  ~vartree() {}
  rpnbase* copy() const;

  void draw( rpnprogram* p, unsigned int depth );

  string const name() const { return string("tree"); }

  void eval( deque<rpnbase*>& ds );
};

class varpwd : public rpnfunction
{
public:

  varpwd() {}
  varpwd(deque<rpnbase*>& ds, bool const evaluate=true);
  ~varpwd() {}
  rpnbase* copy() const;

  string const name() const { return string("pwd"); }

  void eval( deque<rpnbase*>& ds );
};

class pathtoggle : public rpnfunction
{
public:

  pathtoggle() {}
  pathtoggle(deque<rpnbase*>& ds, bool const evaluate=true);
  ~pathtoggle() {}
  rpnbase* copy() const;

  string const name() const { return string("path!"); }

  void visit(deque<rpnbase*>& ds,rpnstring& path);
  void visit(deque<rpnbase*>& ds,rpnprogram& path);

  void eval( deque<rpnbase*>& ds );
};

class varinc: public rpnfunction
{
public:

  varinc() {}
  varinc(deque<rpnbase*>& ds, bool const evaluate=true);
  ~varinc() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpnstring& s);
  void visit(deque<rpnbase*>& ds,rpninteger& n);
  void visit(deque<rpnbase*>& ds,rpnreal& n);

  string const name() const { return string("++"); }

  void eval( deque<rpnbase*>& ds );
};

class vardec: public rpnfunction
{
public:

  vardec() {}
  vardec(deque<rpnbase*>& ds, bool const evaluate=true);
  ~vardec() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpnstring& s);
  void visit(deque<rpnbase*>& ds,rpninteger& n);
  void visit(deque<rpnbase*>& ds,rpnreal& n);

  string const name() const { return string("--"); }

  void eval( deque<rpnbase*>& ds );
};

class varexists: public rpnfunction
{
public:

  varexists() {}
  varexists(deque<rpnbase*>& ds, bool const evaluate=true);
  ~varexists() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpnstring& n);

  string const name() const { return string("isvar"); }

  void eval( deque<rpnbase*>& ds );
};

class varreplace: public rpnfunction
{
public:

  varreplace() {}
  varreplace(deque<rpnbase*>& ds, bool const evaluate=true);
  ~varreplace() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpnstring& n);
  void visit(deque<rpnbase*>& ds,rpninteger& k);

  string const name() const { return string("="); }

  void eval( deque<rpnbase*>& ds );
};

class varrecall: public rpnfunction
{
public:

  varrecall() {}
  varrecall(deque<rpnbase*>& ds, bool const evaluate=true);
  ~varrecall() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpnstring& n);
  void visit(deque<rpnbase*>& ds,rpninteger& n);


  string const name() const { return string("rcl"); }

  void eval( deque<rpnbase*>& ds );
};

class rpnnot: public rpnfunction
{
public:

  rpnnot() {}
  rpnnot(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpnnot() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpnreal& n);
  void visit(deque<rpnbase*>& ds,rpninteger& n);

  string const name() const { return string("!"); }

  void eval( deque<rpnbase*>& ds );
};

class rpnneg: public rpnfunction
{
public:

  rpnneg() {}
  rpnneg(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpnneg() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpninteger& n);
  void visit(deque<rpnbase*>& ds,rpnreal& n);
  void visit(deque<rpnbase*>& ds,rpncomplex& n);

  string const name() const { return string("neg"); }

  void eval( deque<rpnbase*>& ds );
};


class rpnadd: public rpnfunction
{
public:

  rpnadd() {}
  rpnadd(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpnadd() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpninteger& n);
  void visit(deque<rpnbase*>& ds,rpnreal& n);
  void visit(deque<rpnbase*>& ds,rpncomplex& n);

  string const name() const { return string("+"); }

  void eval( deque<rpnbase*>& ds );
};


class rpnmultiply: public rpnfunction
{
public:

  rpnmultiply() {}
  rpnmultiply(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpnmultiply() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpninteger& n);
  void visit(deque<rpnbase*>& ds,rpnreal& n);
  void visit(deque<rpnbase*>& ds,rpncomplex& n);

  string const name() const { return string("*"); }

  void eval( deque<rpnbase*>& ds );
};


class rpnlessthan: public rpnfunction
{
public:

  rpnlessthan() {}
  rpnlessthan(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpnlessthan() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpnreal& n);
  void visit(deque<rpnbase*>& ds,rpninteger& n);

  string const name() const { return string("<"); }

  void eval( deque<rpnbase*>& ds );
};

class rpnlessthanequal: public rpnfunction
{
public:

  rpnlessthanequal() {}
  rpnlessthanequal(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpnlessthanequal() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpnreal& n);
  void visit(deque<rpnbase*>& ds,rpninteger& n);

  string const name() const { return string("<="); }

  void eval( deque<rpnbase*>& ds );
};

class rpngreaterthanequal: public rpnfunction
{
public:

  rpngreaterthanequal() {}
  rpngreaterthanequal(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpngreaterthanequal() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpnreal& n);
  void visit(deque<rpnbase*>& ds,rpninteger& n);

  string const name() const { return string(">="); }

  void eval( deque<rpnbase*>& ds );
};

class rpngreaterthan: public rpnfunction
{
public:

  rpngreaterthan() {}
  rpngreaterthan(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpngreaterthan() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpnreal& n);
  void visit(deque<rpnbase*>& ds,rpninteger& n);

  string const name() const { return string(">"); }

  void eval( deque<rpnbase*>& ds );
};

class rpnequal: public rpnfunction
{
public:

  rpnequal() {}
  rpnequal(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpnequal() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpnreal& n);
  void visit(deque<rpnbase*>& ds,rpninteger& n);

  string const name() const { return string("=="); }

  void eval( deque<rpnbase*>& ds );
};

class rpnfor: public rpnfunction
{
public:

  rpnfor() {}
  rpnfor(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpnfor() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpnprogram& n);

  string const name() const { return string("for"); }

  void eval( deque<rpnbase*>& ds );
};

class rpnforn: public rpnfunction
{
public:

  rpnforn() {}
  rpnforn(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpnforn() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpnprogram& n);
  void visit(deque<rpnbase*>& ds,rpninteger& n);

  string const name() const { return string("forn"); }

  void eval( deque<rpnbase*>& ds );
};


class prognew: public rpnfunction
{
public:

  prognew() {}
  prognew(deque<rpnbase*>& ds, bool const evaluate=true);
  ~prognew() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpninteger& n);

  string const name() const { return string("pnew"); }

  void eval( deque<rpnbase*>& ds );
};


class progdecompose: public rpnfunction
{
public:

  progdecompose() {}
  progdecompose(deque<rpnbase*>& ds, bool const evaluate=true);
  ~progdecompose() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpnprogram& p);

  string const name() const { return string("pnew!"); }

  void eval( deque<rpnbase*>& ds );
};


class progrev: public rpnfunction
{
public:

  progrev() {}
  progrev(deque<rpnbase*>& ds, bool const evaluate=true);
  ~progrev() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpnprogram& pr);

  string const name() const { return string("prev"); }

  void eval( deque<rpnbase*>& ds );
};

class rpnsubtract: public rpnfunction
{
public:

  rpnsubtract() {}
  rpnsubtract(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpnsubtract() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpninteger& n);
  void visit(deque<rpnbase*>& ds,rpnreal& n);
  void visit(deque<rpnbase*>& ds,rpncomplex& n);

  string const name() const { return string("-"); }

  void eval( deque<rpnbase*>& ds );
};

class rpndivide: public rpnfunction
{
public:

  rpndivide() {}
  rpndivide(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpndivide() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpninteger& n);
  void visit(deque<rpnbase*>& ds,rpnreal& n);
  void visit(deque<rpnbase*>& ds,rpncomplex& n);

  string const name() const { return string("/"); }

  void eval( deque<rpnbase*>& ds );
};

class isrpnstring: public rpnfunction
{
public:

  isrpnstring() {}
  isrpnstring(deque<rpnbase*>& ds, bool const evaluate=true);
  ~isrpnstring() {}
  rpnbase* copy() const;

  string const name() const { return string("isstring"); }

  void eval( deque<rpnbase*>& ds );
};

class isrpninteger: public rpnfunction
{
public:

  isrpninteger() {}
  isrpninteger(deque<rpnbase*>& ds, bool const evaluate=true);
  ~isrpninteger() {}
  rpnbase* copy() const;

  string const name() const { return string("isinteger"); }

  void eval( deque<rpnbase*>& ds );
};

class isrpnreal : public rpnfunction
{
public:

  isrpnreal() {}
  isrpnreal(deque<rpnbase*>& ds, bool const evaluate=true);
  ~isrpnreal() {}
  rpnbase* copy() const;

  string const name() const { return string("isreal"); }

  void eval( deque<rpnbase*>& ds );
};

class isrpncomplex : public rpnfunction
{
public:

  isrpncomplex() {}
  isrpncomplex(deque<rpnbase*>& ds, bool const evaluate=true);
  ~isrpncomplex() {}
  rpnbase* copy() const;

  string const name() const { return string("iscomplex"); }

  void eval( deque<rpnbase*>& ds );
};

class isrpnprogram : public rpnfunction
{
public:

  isrpnprogram() {}
  isrpnprogram(deque<rpnbase*>& ds, bool const evaluate=true);
  ~isrpnprogram() {}
  rpnbase* copy() const;

  string const name() const { return string("isprogram"); }

  void eval( deque<rpnbase*>& ds );
};

class pathcd: public rpnfunction
{
public:

  pathcd() {}
  pathcd(deque<rpnbase*>& ds, bool const evaluate=true);
  ~pathcd() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpnstring& s);
  void visit(deque<rpnbase*>& ds,rpnprogram& p);

  string const name() const { return string("cd"); }

  void eval( deque<rpnbase*>& ds );
};

class pathquery: public rpnfunction
{
public:

  pathquery() {}
  pathquery(deque<rpnbase*>& ds, bool const evaluate=true);
  ~pathquery() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpnstring& s);

  string const name() const { return string("ispath"); }

  void eval( deque<rpnbase*>& ds );
};

class varmv: public rpnfunction
{
public:

  varmv() {}
  varmv(deque<rpnbase*>& ds, bool const evaluate=true);
  ~varmv() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpnstring& s);

  string const name() const { return string("mv"); }

  void eval( deque<rpnbase*>& ds );
};

class rpncp: public rpnfunction
{
public:

  rpncp() {}
  rpncp(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpncp() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpnstring& s);

  string const name() const { return string("cp"); }

  void eval( deque<rpnbase*>& ds );
};

class rpninsert : public rpnfunction
{
public:

  rpninsert() {}
  rpninsert(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpninsert() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpninteger& n);

  string const name() const { return string("insert"); }

  void eval( deque<rpnbase*>& ds );
};

class rpnerase : public rpnfunction
{
public:

  rpnerase() {}
  rpnerase(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpnerase() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpninteger& n);

  string const name() const { return string("delete"); }

  void eval( deque<rpnbase*>& ds );
};

class rpnpointermake : public rpnfunction
{
public:

  rpnpointermake() {}
  rpnpointermake(deque<rpnbase*>& ds, bool const evaluate=false);
  ~rpnpointermake() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpninteger& n);
  void visit(deque<rpnbase*>& ds,rpnstring& s);

  string const name() const { return string("->"); }

  void eval( deque<rpnbase*>& ds );
};

class rpnvectormake : public rpnfunction
{
public:

  rpnvectormake() {}
  rpnvectormake(deque<rpnbase*>& ds, bool const evaluate=false);
  ~rpnvectormake() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpninteger& n);
  void visit(deque<rpnbase*>& ds,rpnstring& s);

  string const name() const { return string("[]"); }

  void eval( deque<rpnbase*>& ds );
};

class rpnvectorpointermake : public rpnfunction
{
public:

  rpnvectorpointermake() {}
  rpnvectorpointermake(
    deque<rpnbase*>& ds, bool const evaluate=false);
  ~rpnvectorpointermake() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpnvector& v);
  void visit(deque<rpnbase*>& ds,rpnstring& s);
  void visit(deque<rpnbase*>& ds,rpninteger& k);

  string const name() const { return string("->[]"); }

  void eval( deque<rpnbase*>& ds );
};

class pstream: public rpnfunction
{
public:

  pstream() {}
  pstream(deque<rpnbase*>& ds, bool const evaluate=true);
  ~pstream() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpnprogram& pr);

  string const name() const 
    { return string("pstream"); }

  void eval( deque<rpnbase*>& ds );
};

class rpnintegerhex : public rpnfunction
{
public:

  rpnintegerhex() {}
  rpnintegerhex(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpnintegerhex() {}
  rpnbase* copy() const;

  string const name() const { return string("hex"); }

  void eval( deque<rpnbase*>& ds );
};

class rpnintegeroct : public rpnfunction
{
public:

  rpnintegeroct() {}
  rpnintegeroct(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpnintegeroct() {}
  rpnbase* copy() const;

  string const name() const { return string("oct"); }

  void eval( deque<rpnbase*>& ds );
};

class rpnintegerdec : public rpnfunction
{
public:

  rpnintegerdec() {}
  rpnintegerdec(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpnintegerdec() {}
  rpnbase* copy() const;

  string const name() const { return string("dec"); }

  void eval( deque<rpnbase*>& ds );
};

class rpnintegerbin : public rpnfunction
{
public:

  rpnintegerbin() {}
  rpnintegerbin(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpnintegerbin() {}
  rpnbase* copy() const;

  string const name() const { return string("binary"); }

  void eval( deque<rpnbase*>& ds );
};

class rpnbitnot: public rpnfunction
{
public:

  rpnbitnot() {}
  rpnbitnot(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpnbitnot() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpninteger& n);

  string const name() const { return string("not"); }

  void eval( deque<rpnbase*>& ds );
};

class rpnbitxor: public rpnfunction
{
public:

  rpnbitxor() {}
  rpnbitxor(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpnbitxor() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpninteger& n);

  string const name() const { return string("xor"); }

  void eval( deque<rpnbase*>& ds );
};

class rpnbitor: public rpnfunction
{
public:

  rpnbitor() {}
  rpnbitor(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpnbitor() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpninteger& n);

  string const name() const { return string("or"); }

  void eval( deque<rpnbase*>& ds );
};

class rpnbitand: public rpnfunction
{
public:

  rpnbitand() {}
  rpnbitand(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpnbitand() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpninteger& n);

  string const name() const { return string("and"); }

  void eval( deque<rpnbase*>& ds );
};

class rpnbitshiftleft: public rpnfunction
{
public:

  rpnbitshiftleft() {}
  rpnbitshiftleft(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpnbitshiftleft() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpninteger& n);

  string const name() const { return string("shl"); }

  void eval( deque<rpnbase*>& ds );
};

class rpnbitshiftright: public rpnfunction
{
public:

  rpnbitshiftright() {}
  rpnbitshiftright(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpnbitshiftright() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpninteger& n);

  string const name() const { return string("shr"); }

  void eval( deque<rpnbase*>& ds );
};

class rpnintegerconvert : public rpnfunction
{
public:

  rpnintegerconvert() {}
  rpnintegerconvert(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpnintegerconvert() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpnstring& s);
  void visit(deque<rpnbase*>& ds,rpnreal& n);

  string const name() const { return string("integer"); }

  void eval( deque<rpnbase*>& ds );
};

class rpnstringconvert : public rpnfunction
{
public:

  rpnstringconvert() {}
  rpnstringconvert(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpnstringconvert() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpninteger& n);
  void visit(deque<rpnbase*>& ds,rpnreal& n);

  string const name() const { return string("string"); }

  void eval( deque<rpnbase*>& ds );
};

class rpnfactorial: public rpnfunction
{
public:

  rpnfactorial() {}
  rpnfactorial(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpnfactorial() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpninteger& n);

  string const name() const { return string("factorial"); }

  void eval( deque<rpnbase*>& ds );
};

class rpnmod : public rpnfunction
{
public:

  rpnmod() {}
  rpnmod(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpnmod() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpninteger& n);

  string const name() const { return string("mod"); }

  void eval( deque<rpnbase*>& ds );
};

class rpnascii : public rpnfunction
{
public:

  rpnascii() {}
  rpnascii(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpnascii() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpninteger& n);
  void visit(deque<rpnbase*>& ds,rpnstring& s);

  string const name() const { return string("ascii"); }

  void eval( deque<rpnbase*>& ds );
};

class rpngcd : public rpnfunction
{
public:

  rpngcd() {}
  rpngcd(deque<rpnbase*>& ds, bool const evaluate=true);
  ~rpngcd() {}
  rpnbase* copy() const;

  void visit(deque<rpnbase*>& ds,rpninteger& n);

  string const name() const { return string("gcd"); }

  void eval( deque<rpnbase*>& ds );
};









#endif




