243 lines
8.0 KiB
C++
Executable File

#ifndef __EXPR_H
#define __EXPR_H
#ifndef __STRINGS_H
#include <strings.h>
#endif
#ifndef __REAL_H
#include <real.h>
#endif
#ifndef __ARRAY_H
#include <array.h>
#endif
// @T
// @DES I simboli/istruzioni possibili
// @T
enum TCodesym { _invalid, _endsym, _comma, _lpar, _rpar, _variable,
_number, _string, _plus, _minus, _multiply, _divide,
_chgs, _and, _or, _not, _equal, _match, _noteq, _lt, _gt,
_lteq, _gteq, _sqrt, _sqr, _exp10, _exp, _log10, _log,
_sin, _cos, _tan, _left, _right, _pow, _min, _max, _mid,
_upper } ;
// @DES I tipi di espressioni definiti
// @T
enum TTypeexp { _numexpr, _strexpr } ;
// @END
// @C
// Classe TValue : public TObject
// @END
class TValue : public TObject
{
// @DPRIV
real _r; // Valore real
TString _s; // Valore in formato stringa
public:
// @FPUB
TValue& operator =(const TValue& val) { _s = val._s; _r = val._r; return *this;} // Operatore = tra oggetti TValue
const real& number() const { return _r;} // Ritorna il valore numerico
const char* string() const { return (const char*) _s;} // Ritorna il valore come stringa
void set(const real& val) { _r = val; _s = val.string();} // Real
void set(const char* val) { _s = val; _r = real(val);} // Stringa
// @DES Costruttori. Inizializzano TValue con vari oggetti
// @FPUB
TValue(const real& val) { _r = val; _s = val.string();} // Real
TValue(const char* val) { _s = val; _r = real(val);} // Stringa
TValue(const TValue& val) { *this = val; } // Altro TValue
TValue() { _r = 0.00; _s = ""; } // 0,0 e ""
};
#ifdef __EXPR_CPP
#define extern
#endif
// @DPUB
extern TValue nulltvalue;
// @END
#undef extern
// @C
// Classe TCode : public TObject
// @END
class TCode : public TObject
{
// @DPRIV
TCodesym _sym; // Simbolo-istruzione-codice
TValue _val; // Valore
public:
// @FPUB
TCode& operator =(const TCode& b);
void set(TCodesym sym, const TValue& val = nulltvalue) { _sym = sym; _val = val; } // Inizializza simbolo = sym e valore = val
TCodesym getsym() const { return _sym;} // Ritorna il simbolo _sym
const real& number() const { return _val.number();} // Ritorna il valore _val come real
const char* string() const { return _val.string();} // Ritorna il valore _val come stringa
TCode() {set(_invalid);} // Costruttore, inizializza simbolo con "invalid", valore a nullvalue
TCode(TCodesym sym, const TValue& val = nulltvalue) { set(sym, val);} // Costruttore, inizializza simbolo con sym e valore con val
};
// @C
// Classe TCodearray : public TObject
//
// L'array di istruzioni
//
// @END
class TCodearray : public TObject
{
// @DPRIV
int _last; // Numero di istruzioni
int _ip; // Puntatore all'istruzione corrente (Istruction pointer)
TArray _rpn; // Array
// @END
public:
// @FPUB
void clear(); // Cancella contenuto array
void add(TCodesym sym, const TValue& val = nulltvalue); // Aggiunge un'istruzione all'array
void begin() { _ip = 0;} // Mette all'inizio il puntatore all'istruzione corrente
TCode& step() { return (TCode&) _rpn[end() ? _ip : _ip++];} // Incrementa istruction pointer
bool end() const { return ((TCode&) _rpn[_ip]).getsym() == _endsym;} // Ritorna vero se _ip ha raggiunto il simbolo di fine codice
void backtrace(int step = 1) { _ip > step ? _ip -= step : begin(); }
TCodearray(int size = 50); // Il costruttore crea un array di 10 elementi
};
// @C
// Classe TVar : public TObject
// @END
class TVar : public TObject
{
// @DPRIV
TString _name; // Nome variabile
TValue _val; // Valore
public:
// @DES Operatore = tra vari oggetti
// @FPUB
const char* operator =(const char* val) { _val.set(val); return val;}
const real& operator =(const real& val) { _val.set(val); return val;}
TVar& operator =(const TValue& val) { _val = val; return *this;}
TVar& operator =(const TVar& var) { _name = var._name ; _val = var._val; return *this;}
void set(const char* name, const TValue& val = nulltvalue) { _name = name ; _val = val;}
void setname(const char* name) { _name = name;} // Setta a name il nome della variabile
const char* getname() const { return _name;} // Ritorna il nome della variabile
operator TValue&() { return _val;} // Ritorna _val (un TValue)
const real& number() const { return _val.number();} // Ritorna il valore real della variabile
const char* string() const { return _val.string();} // Ritorna il valore stringa della variabile
// @DES Costruttori
// @FPUB
TVar() { _name = ""; _val = nulltvalue;}
TVar(const char* name, const TValue& val = nulltvalue) { _name = name; _val = val;}
TVar(TVar& v) { _name = v._name; _val = v._val;}
};
// @C
// class TVararray : public TObject
// @END
class TVararray : public TObject
{
// @DPRIV
int _last; // Numero di variabili
TArray _array; // Array
// @END
public:
// @FPUB
void clear() { _last = 0; } // Cancella contenuto array
void add(const TVar& var); // Aggiunge un oggetto TVar
void add(const char* name, const TValue& val = nulltvalue); // Aggiunge un nome di variabile e il suo valore
const char* varname(int varnum) const { return varnum < _array.items() ? ((TVar&) _array[varnum]).getname() : "";} // Ritorna il nome della variabile di posto varnum
// @DES Metodi di inizializzazione
// @FPUB
void set(const char* varname, const real& val);
void set(const char* varname, const char* val);
void set(int varnum, const real& val) { if (varnum < _array.items()) ((TVar&) _array[varnum]) = val;}
void set(int varnum, const char* val) { if (varnum < _array.items()) ((TVar&) _array[varnum]) = val;}
// @DES Metodi di interrogazione
// @FPUB
const real& getnum(const char* varname);
const real& getnum(int varnum);
const char* getstring(const char* varname);
const char* getstring(int varnum);
int numvar() const { return _last;} // Ritorna il numero di variabili utilizzate
TVararray(int size = 10);
};
// @C
// class TExpression : public TObject
// @END
class TExpression : public TObject
{
// @DPRIV
TCodearray _code; // Array di codice
TVararray _var; // Array di variabili
TValue _val; // Valore dell'espressione
bool _dirty; // Vero se l'espressione e' stata modificata
TTypeexp _type; // Tipo dell'espressione
TString _original; // stringa originale
// @END
// @FPROT
protected:
void eval(); // Valuta l'espressione
TCodesym __gettoken(bool reduct = FALSE);
TCodesym __factor(TCodesym startsym);
TCodesym __term(TCodesym startsym);
TCodesym __expression(TCodesym startsym);
virtual void print_on(ostream& out) const ;
bool compile(const char* expression, TTypeexp type); // Compila l'espressione
public:
// @FPUB
operator const real&(); // Ritorna il valore real dell'espressione
operator const char*(); // Ritorna il valore come stringa
operator bool(); // Ritorna il valore come booleano
// @DES Metodi di interrogazione
// @FPUB
// Ritorna il nome della variabile di posto varnum
const char* varname(int varnum) const { return _var.varname(varnum); }
// Ritorna il numero di variabili nell'espressione
int numvar() const { return _var.numvar(); }
const TTypeexp type() const { return _type; }
TCodearray& code() const { return (TCodearray&)_code; }
const TVararray& vars() const { return _var; }
// @DES Metodi di inizializzazione
// @FPUB
void setvar(const char* varname, const real& val);
void setvar(int varnum, const real& val);
void setvar(const char* varname, const char* val);
void setvar(int varnum, const char* val);
void set_type(const TTypeexp type) { _type = type; }
bool set(const char* expression, TTypeexp type = _numexpr);
TExpression(const char* expression, TTypeexp type = _numexpr);
TExpression(TTypeexp type = _numexpr);
};
#endif // __EXPR_H