| □ C++版 |
| InterpreterSample.cpp |
// Copyright(C) 2004 Yoshinori Oota All rights reserved.
#include <string>
#include <iostream>
#include "QueryParser.h"
#include "Expression.h"
#include "calcVisitor.h"
#include "dumpVisitor.h"
#define LINE_BUF 1024
int main(int argc, char* argv[]) {
using namespace std;
QueryParser parser;
dumpVisitor* dump = new dumpVisitor();
calcVisitor* calc = new calcVisitor();
char buffer[LINE_BUF];
while (true) {
cout << "> ";
cin.getline(buffer, LINE_BUF);
string query = buffer;
if (query == "end") {
break;
}
Expression* exp = parser.parse(query);
if (exp == NULL) {
continue;
}
std::cout << "Expression: ";
exp->accept(dump);
exp->accept(calc);
std::cout << " = " << calc->getResult() << std::endl;
calc->clear();
delete exp;
}
delete dump;
delete calc;
}
|
| QueryParser |
// Copyright(C) 2004 Yoshinori Oota All rights reserved.
#ifndef QUERYPARSER_HEADER_GUARD__
#define QUERYPARSER_HEADER_GUARD__
#include <string>
#include <stack>
class Expression;
class QueryParser {
public:
QueryParser();
~QueryParser();
Expression* parse(const std::string& line);
private:
void clearStack();
Expression* cur_;
std::stack<Expression*> stk_;
};
#endif // QUERYPARSER_HEADER_GUARD__
|
// Copyright(C) 2004 Yoshinori Oota All rights reserved.
#include "QueryParser.h"
#include "terminalExpression.h"
#include "bracketExpression.h"
#include "addExpression.h"
#include "subExpression.h"
#include "mulExpression.h"
#include "divExpression.h"
#include <sstream>
#include <iostream>
#include <cstdlib>
QueryParser::QueryParser() : cur_(NULL) { }
QueryParser::~QueryParser() {
cur_ = NULL;
clearStack();
}
Expression* QueryParser::parse(const std::string& line) {
using namespace std;
istringstream is(line);
string token;
try {
Expression* exp = NULL;
cur_ = new bracketExpression();
while (is >> token) {
if (token == "+") {
cur_ = new addExpression(cur_);
} else if (token == "-") {
cur_ = new subExpression(cur_);
} else if (token == "*") {
cur_ = new mulExpression(cur_);
} else if (token == "/") {
cur_ = new divExpression(cur_);
} else if (token == "(") {
stk_.push(cur_);
cur_ = new bracketExpression();
} else if (token == ")") {
exp = stk_.top();
if (exp->isOperator()) {
exp->addRightHandSide(cur_);
cur_ = exp;
} else {
delete exp;
}
stk_.pop();
} else {
exp = new terminalExpression(atoi(token.c_str()));
if (cur_->isOperator()) {
cur_->addRightHandSide(exp);
} else {
delete cur_;
cur_ = exp;
}
}
}
} catch (invalid_argument& e) {
cerr << "exception: " << e.what() << endl;
clearStack();
if (cur_ != NULL) {
delete cur_;
cur_ = NULL;
}
}
if (!stk_.empty()) {
cerr << "parse error. " << endl;
clearStack();
if (cur_ != NULL) {
delete cur_;
cur_ = NULL;
}
}
return cur_;
}
void QueryParser::clearStack() {
while (!stk_.empty()) {
Expression* exp = stk_.top();
delete exp;
stk_.pop();
}
}
|
| Expression |
// Copyright(C) 2004 Yoshinori Oota All rights reserved.
#ifndef EXPRESSION_HEADER_GUARD__
#define EXPRESSION_HEADER_GUARD__
#include <stdexcept>
class Visitor;
class Expression {
public:
Expression();
virtual ~Expression();
virtual void accept(Visitor* v) const = 0;
protected:
friend class QueryParser;
virtual void addRightHandSide(Expression* exp) throw (std::invalid_argument) = 0;
virtual void addLeftHandSide(Expression* exp) throw (std::invalid_argument) = 0;
virtual bool isOperator() const = 0;
};
#endif // EXPRESSION_HEADER_GUARD__
|
// Copyright(C) 2004 Yoshinori Oota All rights reserved.
#include "Expression.h"
Expression::Expression() { }
Expression::~Expression() { }
|
| terminalExpression |
// Copyright(C) 2004 Yoshinori Oota All rights reserved.
#ifndef TERMINALEXPRESSION_HEADER_GUARD__
#define TERMINALEXPRESSION_HEADER_GUARD__
#include "Expression.h"
class terminalExpression : public Expression {
public:
terminalExpression(int number);
virtual ~terminalExpression();
virtual void accept(Visitor* v) const;
int getValue() const;
protected:
virtual void addRightHandSide(Expression* rhs) throw (std::invalid_argument);
virtual void addLeftHandSide(Expression* lhs) throw (std::invalid_argument);
virtual bool isOperator() const;
private:
int number_;
};
#endif // TERMINALEXPRESSION_HEADER_GUARD__
|
// Copyright(C) 2004 Yoshinori Oota All rights reserved.
#include <iostream>
#include "terminalExpression.h"
#include "Visitor.h"
terminalExpression::terminalExpression(int number) : number_(number) { }
terminalExpression::~terminalExpression() { }
void terminalExpression::addRightHandSide(Expression* exp1) throw (std::invalid_argument) {
throw std::invalid_argument("invalid call terminalExpression::addRightHandSide()");
}
void terminalExpression::addLeftHandSide(Expression* exp2) throw (std::invalid_argument) {
throw std::invalid_argument("invalid call terminalExpression::addLeftHandSide()");
}
bool terminalExpression::isOperator() const {
return false;
}
void terminalExpression::accept(Visitor* v) const {
v->Visit(this);
}
int terminalExpression::getValue() const {
return number_;
}
|
| bracketExpression |
// Copyright(C) 2004 Yoshinori Oota All rights reserved.
#ifndef BRACKETEXPRESSION_HEADER_GUARD__
#define BRACKETEXPRESSION_HEADER_GUARD__
#include "Expression.h"
class bracketExpression : public Expression {
public:
bracketExpression();
virtual ~bracketExpression();
virtual void accept(Visitor* v) const;
protected:
virtual void addRightHandSide(Expression* exp1) throw (std::invalid_argument);
virtual void addLeftHandSide(Expression* exp2) throw (std::invalid_argument);
virtual bool isOperator() const;
};
#endif // BRACKETEXPRESSION_HEADER_GUARD__
|
// Copyright(C) 2004 Yoshinori Oota All rights reserved.
#include "bracketExpression.h"
#include "Visitor.h"
bracketExpression::bracketExpression() { }
bracketExpression::~bracketExpression() { }
void bracketExpression::addRightHandSide(Expression* exp1) throw (std::invalid_argument){
throw std::invalid_argument("invalid call bracketExpression::addRightHandSide()");
}
void bracketExpression::addLeftHandSide(Expression* exp2) throw (std::invalid_argument){
throw std::invalid_argument("invalid call bracketExpression::addLeftHandSide()");
}
void bracketExpression::accept(Visitor* v) const {
// do nothing
}
bool bracketExpression::isOperator() const {
return false;
}
|
| addExpression |
// Copyright(C) 2004 Yoshinori Oota All rights reserved.
#ifndef ADDEXPRESSION_HEADER_GUARD__
#define ADDEXPRESSION_HEADER_GUARD__
#include "Expression.h"
class addExpression : public Expression {
public:
addExpression();
addExpression(Expression* lhs);
virtual ~addExpression();
virtual void accept(Visitor* v) const;
const Expression* getRightHandSide() const;
const Expression* getLeftHandSide() const;
protected:
friend class QueryParser;
virtual void addRightHandSide(Expression* rhs) throw (std::invalid_argument);
virtual void addLeftHandSide(Expression* lhs) throw (std::invalid_argument);
virtual bool isOperator() const;
private:
Expression* lhs_;
Expression* rhs_;
};
#endif // ADDEXPRESSION_HEADER_GUARD__
|
// Copyright(C) 2004 Yoshinori Oota All rights reserved.
#include "addExpression.h"
#include "Visitor.h"
addExpression::addExpression() : lhs_(0), rhs_(0) { }
addExpression::addExpression(Expression* lhs) : lhs_(lhs), rhs_(0) { }
addExpression::~addExpression() {
if (lhs_ != 0) {
delete lhs_;
}
if (rhs_ != 0) {
delete rhs_;
}
}
void addExpression::addRightHandSide(Expression* rhs) throw (std::invalid_argument) {
rhs_ = rhs;
}
void addExpression::addLeftHandSide(Expression* lhs) throw (std::invalid_argument) {
lhs_ = lhs;
}
bool addExpression::isOperator() const {
return true;
}
const Expression* addExpression::getRightHandSide() const {
return rhs_;
}
const Expression* addExpression::getLeftHandSide() const {
return lhs_;
}
void addExpression::accept(Visitor* v) const {
v->Visit(this);
}
|
| subExpression |
// Copyright(C) 2004 Yoshinori Oota All rights reserved.
#ifndef SUBEXPRESSION_HEADER_GUARD__
#define SUBEXPRESSION_HEADER_GUARD__
#include "Expression.h"
class subExpression : public Expression {
public:
subExpression();
subExpression(Expression* lhs);
virtual ~subExpression();
virtual void accept(Visitor* v) const;
const Expression* getRightHandSide() const;
const Expression* getLeftHandSide() const;
protected:
friend class QueryParser;
virtual void addRightHandSide(Expression* rhs) throw (std::invalid_argument);
virtual void addLeftHandSide(Expression* lhs) throw (std::invalid_argument);
virtual bool isOperator() const;
private:
Expression* lhs_;
Expression* rhs_;
};
#endif // SUBEXPRESSION_HEADER_GUARD__
|
// Copyright(C) 2004 Yoshinori Oota All rights reserved.
#include "subExpression.h"
#include "Visitor.h"
subExpression::subExpression() : lhs_(0), rhs_(0) { }
subExpression::subExpression(Expression* lhs) : lhs_(lhs), rhs_(0) { }
subExpression::~subExpression() {
if (lhs_ != 0) {
delete lhs_;
}
if (rhs_ != 0) {
delete rhs_;
}
}
void subExpression::addRightHandSide(Expression* rhs) throw (std::invalid_argument) {
rhs_ = rhs;
}
void subExpression::addLeftHandSide(Expression* lhs) throw (std::invalid_argument) {
lhs_ = lhs;
}
bool subExpression::isOperator() const {
return true;
}
const Expression* subExpression::getRightHandSide() const {
return rhs_;
}
const Expression* subExpression::getLeftHandSide() const {
return lhs_;
}
void subExpression::accept(Visitor* v) const {
v->Visit(this);
}
|
| mulExpression |
// Copyright(C) 2004 Yoshinori Oota All rights reserved.
#ifndef MULEXPRESSION_HEADER_GUARD__
#define MULEXPRESSION_HEADER_GUARD__
#include "Expression.h"
class mulExpression : public Expression {
public:
mulExpression();
mulExpression(Expression* lhs);
virtual ~mulExpression();
virtual void accept(Visitor* v) const;
const Expression* getRightHandSide() const;
const Expression* getLeftHandSide() const;
protected:
friend class QueryParser;
virtual void addRightHandSide(Expression* rhs) throw (std::invalid_argument);
virtual void addLeftHandSide(Expression* lhs) throw (std::invalid_argument);
virtual bool isOperator() const;
private:
Expression* lhs_;
Expression* rhs_;
};
#endif // MULEXPRESSION_HEADER_GUARD__
|
// Copyright(C) 2004 Yoshinori Oota All rights reserved.
#include "mulExpression.h"
#include "Visitor.h"
mulExpression::mulExpression() : lhs_(0), rhs_(0) { }
mulExpression::mulExpression(Expression* lhs) : lhs_(lhs), rhs_(0) { }
mulExpression::~mulExpression() {
if (lhs_ != 0) {
delete lhs_;
}
if (rhs_ != 0) {
delete rhs_;
}
}
void mulExpression::addRightHandSide(Expression* rhs) throw (std::invalid_argument) {
rhs_ = rhs;
}
void mulExpression::addLeftHandSide(Expression* lhs) throw (std::invalid_argument) {
lhs_ = lhs;
}
bool mulExpression::isOperator() const {
return true;
}
const Expression* mulExpression::getRightHandSide() const {
return rhs_;
}
const Expression* mulExpression::getLeftHandSide() const {
return lhs_;
}
void mulExpression::accept(Visitor* v) const {
v->Visit(this);
}
|
| divExpression |
// Copyright(C) 2004 Yoshinori Oota All rights reserved.
#ifndef DIVEXPRESSION_HEADER_GUARD__
#define DIVEXPRESSION_HEADER_GUARD__
#include "Expression.h"
class divExpression : public Expression {
public:
divExpression();
divExpression(Expression* lhs);
virtual ~divExpression();
virtual void accept(Visitor* v) const;
const Expression* getRightHandSide() const;
const Expression* getLeftHandSide() const;
protected:
friend class QueryParser;
virtual void addRightHandSide(Expression* rhs) throw (std::invalid_argument);
virtual void addLeftHandSide(Expression* lhs) throw (std::invalid_argument);
virtual bool isOperator() const;
private:
Expression* lhs_;
Expression* rhs_;
};
#endif // DIVEXPRESSION_HEADER_GUARD__
|
// Copyright(C) 2004 Yoshinori Oota All rights reserved.
#include "divExpression.h"
#include "Visitor.h"
divExpression::divExpression() : lhs_(0), rhs_(0) { }
divExpression::divExpression(Expression* lhs) : lhs_(lhs), rhs_(0) { }
divExpression::~divExpression() {
if (lhs_ != 0) {
delete lhs_;
}
if (rhs_ != 0) {
delete rhs_;
}
}
void divExpression::addRightHandSide(Expression* rhs) throw (std::invalid_argument) {
rhs_ = rhs;
}
void divExpression::addLeftHandSide(Expression* lhs) throw (std::invalid_argument) {
lhs_ = lhs;
}
bool divExpression::isOperator() const {
return true;
}
const Expression* divExpression::getRightHandSide() const {
return rhs_;
}
const Expression* divExpression::getLeftHandSide() const {
return lhs_;
}
void divExpression::accept(Visitor* v) const {
v->Visit(this);
}
|
| Visitor |
// Copyright(C) 2004 Yoshinori Oota All rights reserved.
#ifndef VISITOR_HEADER_GUARD__
#define VISITOR_HEADER_GUARD__
class terminalExpression;
class addExpression;
class subExpression;
class mulExpression;
class divExpression;
class Visitor {
public:
Visitor();
virtual ~Visitor();
virtual void Visit(const terminalExpression* exp) = 0;
virtual void Visit(const addExpression* exp) = 0;
virtual void Visit(const subExpression* exp) = 0;
virtual void Visit(const mulExpression* exp) = 0;
virtual void Visit(const divExpression* exp) = 0;
};
#endif // VISITOR_HEADER_GUARD__
|
// Copyright(C) 2004 Yoshinori Oota All rights reserved.
#include "Visitor.h"
Visitor::Visitor() { }
Visitor::~Visitor() { }
|
| dumpVisitor |
// Copyright(C) 2004 Yoshinori Oota All rights reserved.
#ifndef DUMPVISITOR_HEADER_GUARD__
#define DUMPVISITOR_HEADER_GUARD__
#include "Visitor.h"
class dumpVisitor : public Visitor {
public:
dumpVisitor();
virtual ~dumpVisitor();
virtual void Visit(const terminalExpression* exp);
virtual void Visit(const addExpression* exp);
virtual void Visit(const subExpression* exp);
virtual void Visit(const mulExpression* exp);
virtual void Visit(const divExpression* exp);
};
#endif // DUMPVISITOR_HEADER_GUARD__
|
// Copyright(C) 2004 Yoshinori Oota All rights reserved.
#include <iostream>
#include "dumpVisitor.h"
#include "terminalExpression.h"
#include "addExpression.h"
#include "subExpression.h"
#include "mulExpression.h"
#include "divExpression.h"
dumpVisitor::dumpVisitor() { }
dumpVisitor::~dumpVisitor() { }
void dumpVisitor::Visit(const terminalExpression* exp) {
std::cout << exp->getValue();
}
void dumpVisitor::Visit(const addExpression* exp) {
std::cout << "(";
const Expression* lhs = exp->getLeftHandSide();
lhs->accept(this);
std::cout << " + ";
const Expression* rhs = exp->getRightHandSide();
rhs->accept(this);
std::cout << ")";
}
void dumpVisitor::Visit(const subExpression* exp) {
std::cout << "(";
const Expression* lhs = exp->getLeftHandSide();
lhs->accept(this);
std::cout << " - ";
const Expression* rhs = exp->getRightHandSide();
rhs->accept(this);
std::cout << ")";
}
void dumpVisitor::Visit(const mulExpression* exp) {
std::cout << "(";
const Expression* lhs = exp->getLeftHandSide();
lhs->accept(this);
std::cout << " * ";
const Expression* rhs = exp->getRightHandSide();
rhs->accept(this);
std::cout << ")";
}
void dumpVisitor::Visit(const divExpression* exp) {
std::cout << "(";
const Expression* lhs = exp->getLeftHandSide();
lhs->accept(this);
std::cout << " / ";
const Expression* rhs = exp->getRightHandSide();
rhs->accept(this);
std::cout << ")";
}
|
| calcVisitor |
// Copyright(C) 2004 Yoshinori Oota All rights reserved.
#ifndef CALCVISITOR_HEADER_GUARD__
#define CALCVISITOR_HEADER_GUARD__
#include "Visitor.h"
class calcVisitor : public Visitor {
public:
calcVisitor();
virtual ~calcVisitor();
virtual void Visit(const terminalExpression* exp);
virtual void Visit(const addExpression* exp);
virtual void Visit(const subExpression* exp);
virtual void Visit(const mulExpression* exp);
virtual void Visit(const divExpression* exp);
void clear();
int getResult() const;
private:
int value_;
};
#endif // CALCVISITOR_HEADER_GUARD__
|
// Copyright(C) 2004 Yoshinori Oota All rights reserved.
#include "calcVisitor.h"
#include "terminalExpression.h"
#include "addExpression.h"
#include "subExpression.h"
#include "mulExpression.h"
#include "divExpression.h"
calcVisitor::calcVisitor() : value_(0) { }
calcVisitor::~calcVisitor() { }
void calcVisitor::Visit(const terminalExpression* exp) {
value_ = exp->getValue();
}
void calcVisitor::Visit(const addExpression* exp) {
const Expression* lhs = exp->getLeftHandSide();
lhs->accept(this);
int value = value_;
const Expression* rhs = exp->getRightHandSide();
rhs->accept(this);
value_ += value;
}
void calcVisitor::Visit(const subExpression* exp) {
const Expression* lhs = exp->getLeftHandSide();
lhs->accept(this);
int value = value_;
const Expression* rhs = exp->getRightHandSide();
rhs->accept(this);
value_ = value - value_;
}
void calcVisitor::Visit(const mulExpression* exp) {
const Expression* lhs = exp->getLeftHandSide();
lhs->accept(this);
int value = value_;
const Expression* rhs = exp->getRightHandSide();
rhs->accept(this);
value_ = value * value_;
}
void calcVisitor::Visit(const divExpression* exp) {
const Expression* lhs = exp->getLeftHandSide();
lhs->accept(this);
int value = value_;
const Expression* rhs = exp->getRightHandSide();
rhs->accept(this);
value_ = value / value_;
}
void calcVisitor::clear() {
value_ = 0;
}
int calcVisitor::getResult() const {
return value_;
}
|