// rpimpl_oper.h // Copyright (c) Menno Rubingh 2016. Web: [http://rubinghsoftware.de] // // MR Mar 2016. // // OperationXxx classes: // Used internally by the RPInterpreter implementation. // Instance executes a specific operation (changing stack and variables) // during the evaluation of a RP expression. // //--- // Implementation notes: // - All member variables are constants, set via the constructors. // - All member functions are 'const', since they do not change the member variables. // - Member variable cm_cxt: // This is common to all classes (therefore in Base class). // It is passed to the exception thrown on execution error. // It is stored not as a pointer but as a whole instance of the class struct, since // we must store the contents of this struct. So the constructor makes a COPY if the // struct passed as an input parameter. // - The different binary operations are all coded out as individual OperationBinXxx // subclasses, instead of one combined OperationBinary subclass parameterized by an // instance of another pure virtual class hierarchy implementing the various low-level // oerations. The rationale for coding each binary operation out as an individual // OperationBinXxx subclass is to achieve the fastest possible processing speed. // #ifndef _RPIMPL_OPER_H_ #define _RPIMPL_OPER_H_ #include "rpimpl_ex.h" //SContext, Ex. #include "rpimpl_stack.h" //StackDbl. #include "rpimpl_var.h" //VarTable. #include <stdio.h> //FILE. #include <math.h> //pow(). //-------------------------------------------------------------------------------- // The OperationXxx classes. //-------------------------------------------------------------------------------- class OperationBase { protected: SContext const cm_cxt; //Character nr in input string where this lexical element begins. public: OperationBase( SContext const * iCxt ) : cm_cxt( *iCxt ) //Copy struct contents. { } virtual ~OperationBase( void ) { } virtual void print( FILE * oF ) const = 0; virtual void execute( StackDbl * uStack, VarTable * uVars ) const = 0; }; // // The ';' operator: // Check that stacksize == 0, and do nothing else. // class OperationSemicolon : public OperationBase { public: OperationSemicolon( SContext const * iCxt ) : OperationBase( iCxt ) { } void print ( FILE * oF ) const; void execute( StackDbl * uStack, VarTable * uVars ) const; }; // // Push the value of a variable onto stack. // class OperationPushVar : public OperationBase { int const cm_varIndex; //Index in VarTable of the variable to push. public: OperationPushVar( SContext const * iCxt, int iVarIndex ) : OperationBase( iCxt ), cm_varIndex( iVarIndex ) { } void print ( FILE * oF ) const; void execute( StackDbl * uStack, VarTable * uVars ) const; }; // // Pop a value off stack, copy it into a variable. // class OperationPopVar : public OperationBase { int const cm_varIndex; //Index in VarTable of the variable to push. public: OperationPopVar( SContext const * iCxt, int iVarIndex ) : OperationBase( iCxt ), cm_varIndex( iVarIndex ) { } void print ( FILE * oF ) const; void execute( StackDbl * uStack, VarTable * uVars ) const; }; // // Push a constant value onto stack. // class OperationPushConst : public OperationBase { double const cm_value; public: OperationPushConst( SContext const * iCxt, double iVal ) : OperationBase( iCxt ), cm_value(iVal) { } void print ( FILE * oF ) const; void execute( StackDbl * uStack, VarTable * uVars ) const; }; // // Binary operations: // Pop two operands, execute binary operation, push result. // class OperationBinAdd : public OperationBase { public: OperationBinAdd( SContext const * iCxt ) : OperationBase( iCxt ) { } void print ( FILE * oF ) const; void execute( StackDbl * uStack, VarTable * uVars ) const; }; class OperationBinSub : public OperationBase { public: OperationBinSub( SContext const * iCxt ) : OperationBase( iCxt ) { } void print ( FILE * oF ) const; void execute( StackDbl * uStack, VarTable * uVars ) const; }; class OperationBinMul : public OperationBase { public: OperationBinMul( SContext const * iCxt ) : OperationBase( iCxt ) { } void print ( FILE * oF ) const; void execute( StackDbl * uStack, VarTable * uVars ) const; }; class OperationBinDiv : public OperationBase { public: OperationBinDiv( SContext const * iCxt ) : OperationBase( iCxt ) { } void print ( FILE * oF ) const; void execute( StackDbl * uStack, VarTable * uVars ) const; }; class OperationBinPow : public OperationBase { public: OperationBinPow( SContext const * iCxt ) : OperationBase( iCxt ) { } void print ( FILE * oF ) const; void execute( StackDbl * uStack, VarTable * uVars ) const; }; #endif //_RPIMPL_OPER_H_