Added scopes

This commit is contained in:
Bobby Lucero 2023-05-31 02:44:39 -04:00
parent 7e0cead697
commit fe26a7c2e0
11 changed files with 100 additions and 11 deletions

View File

@ -15,7 +15,19 @@ public:
std::shared_ptr<Object> get(Token name);
sptr(Environment) enclosing;
Environment(){
enclosing = nullptr;
}
Environment(sptr(Environment) environment) : enclosing(environment)
{
}
private:
std::unordered_map<std::string, sptr(Object)> variables;
};

View File

@ -16,15 +16,22 @@ public:
sptr(Object) visitVariableExpr(sptr(VarExpr) expression) override;
sptr(Object) visitAssignExpr(sptr(AssignExpr) expression) override;
void visitBlockStmt(sptr(BlockStmt) statement) override;
void visitExpressionStmt(sptr(ExpressionStmt) statement) override;
void visitPrintStmt(sptr(PrintStmt) statement) override;
void visitVarStmt(sptr(VarStmt) statement) override;
void interpret(std::vector<sptr(Stmt)> statements);
Interpreter(){
environment = msptr(Environment)();
}
private:
Environment environment;
sptr(Environment) environment;
sptr(Object) evaluate(sptr(Expr) expr);
bool isTruthy(sptr(Object) object);
@ -35,4 +42,6 @@ private:
bool isWholeNumer(double num);
void execute(std::shared_ptr<Stmt> statement);
void executeBlock(std::vector<std::shared_ptr<Stmt>> statements, std::shared_ptr<Environment> env);
};

View File

@ -63,7 +63,6 @@ struct Token
{
TokenType type;
std::string lexeme;
//TODO Object literal;
int line;
};

View File

@ -47,4 +47,6 @@ private:
std::shared_ptr<Stmt> varDeclaration();
std::shared_ptr<Expr> assignment();
std::vector<std::shared_ptr<Stmt>> block();
};

View File

@ -8,9 +8,11 @@
struct ExpressionStmt;
struct PrintStmt;
struct VarStmt;
struct BlockStmt;
struct StmtVisitor
{
virtual void visitBlockStmt(sptr(BlockStmt) stmt) = 0;
virtual void visitExpressionStmt(sptr(ExpressionStmt) stmt) = 0;
virtual void visitPrintStmt(sptr(PrintStmt) stmt) = 0;
virtual void visitVarStmt(sptr(VarStmt) stmt) = 0;
@ -23,6 +25,18 @@ struct Stmt
virtual ~Stmt(){};
};
struct BlockStmt : Stmt, public std::enable_shared_from_this<BlockStmt>
{
const std::vector<sptr(Stmt)> statements;
explicit BlockStmt(std::vector<sptr(Stmt)> statements) : statements(statements)
{
}
void accept(StmtVisitor* visitor) override
{
visitor->visitBlockStmt(shared_from_this());
}
};
struct ExpressionStmt : Stmt, public std::enable_shared_from_this<ExpressionStmt>
{
const sptr(Expr) expression;

View File

@ -17,8 +17,7 @@ struct String : Object
std::string value;
explicit String(std::string str) : value(str) {}
~String(){
std::cout << value.size() << std::endl;
std::cout << "String being destroyed..." << std::endl;
}
};

View File

@ -1 +1,5 @@
10 10;
var a = 1;
{
var a = a + 2;
print a;
}

View File

@ -13,6 +13,11 @@ sptr(Object) Environment::get(Token name)
return variables[name.lexeme];
}
if(enclosing != nullptr)
{
return enclosing->get(name);
}
throw std::runtime_error("Undefined variable '" + name.lexeme + "'.");
}
@ -30,5 +35,11 @@ void Environment::assign(Token name, std::shared_ptr<Object> value) {
return;
}
if(enclosing != nullptr)
{
enclosing->assign(name, value);
return;
}
throw std::runtime_error("Undefined variable '" + name.lexeme + "'.");
}

View File

@ -148,15 +148,19 @@ sptr(Object) Interpreter::visitBinaryExpr(sptr(BinaryExpr) expression)
sptr(Object) Interpreter::visitVariableExpr(sptr(VarExpr) expression)
{
return environment.get(expression->name);
return environment->get(expression->name);
}
sptr(Object) Interpreter::visitAssignExpr(sptr(AssignExpr) expression) {
sptr(Object) value = evaluate(expression->value);
environment.assign(expression->name, value);
environment->assign(expression->name, value);
return value;
}
void Interpreter::visitBlockStmt(std::shared_ptr<BlockStmt> statement) {
executeBlock(statement->statements, msptr(Environment)(environment));
}
void Interpreter::visitExpressionStmt(sptr(ExpressionStmt) statement) {
evaluate(statement->expression);
}
@ -176,7 +180,7 @@ void Interpreter::visitVarStmt(sptr(VarStmt) statement)
//std::cout << "Visit var stmt: " << statement->name.lexeme << " set to: " << stringify(value) << std::endl;
environment.define(statement->name.lexeme, value);
environment->define(statement->name.lexeme, value);
}
void Interpreter::interpret(std::vector<sptr(Stmt)> statements) {
@ -193,7 +197,28 @@ void Interpreter::interpret(std::vector<sptr(Stmt)> statements) {
void Interpreter::execute(sptr(Stmt) statement)
{
try {
statement->accept(this);
}
catch(std::exception &e)
{
std::cout << "ERROR OCCURRED: " << e.what() << std::endl;
return;
}
}
void Interpreter::executeBlock(std::vector<sptr(Stmt)> statements, sptr(Environment) env)
{
sptr(Environment) previous = this->environment;
this->environment = env;
for(sptr(Stmt) s : statements)
{
execute(s);
}
this->environment = previous;
}
sptr(Object) Interpreter::evaluate(sptr(Expr) expr) {

View File

@ -147,6 +147,7 @@ std::vector<sptr(Stmt)> Parser::parse() {
sptr(Stmt) Parser::statement()
{
if(match({PRINT})) return printStatement();
if(match({OPEN_BRACE})) return msptr(BlockStmt)(block());
return expressionStatement();
}
@ -164,6 +165,19 @@ sptr(Stmt) Parser::expressionStatement()
return msptr(ExpressionStmt)(expr);
}
std::vector<sptr(Stmt)> Parser::block()
{
std::vector<sptr(Stmt)> statements;
while(!check(CLOSE_BRACE) && !isAtEnd())
{
statements.push_back(declaration());
}
consume(CLOSE_BRACE, "Expected '}' after block.");
return statements;
}
sptr(Stmt) Parser::declaration()
{
try{

View File

@ -8,8 +8,8 @@
int main(){
Bob bobLang;
//bobLang.runFile("source.bob");
bobLang.runPrompt();
bobLang.runFile("source.bob");
//bobLang.runPrompt();
return 0;
}