12.5 This
This commit is contained in:
parent
591caeb216
commit
21a58ffb20
6 changed files with 26 additions and 2 deletions
|
@ -62,6 +62,11 @@ class Interpreter implements Expr.Visitor<Object>, Stmt.Visitor<Void> {
|
||||||
return value;
|
return value;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Object visitThisExpr(Expr.This expr) {
|
||||||
|
return lookUpVariable(expr.keyword, expr);
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Object visitUnaryExpr(Expr.Unary expr) {
|
public Object visitUnaryExpr(Expr.Unary expr) {
|
||||||
Object right = evaluate(expr.right);
|
Object right = evaluate(expr.right);
|
||||||
|
|
|
@ -11,6 +11,12 @@ class LoxFunction implements LoxCallable {
|
||||||
this.declaration = declaration;
|
this.declaration = declaration;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
LoxFunction bind(LoxInstance instance) {
|
||||||
|
Environment environment = new Environment(closure);
|
||||||
|
environment.define("this", instance);
|
||||||
|
return new LoxFunction(declaration, environment);
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public int arity() {
|
public int arity() {
|
||||||
return declaration.params.size();
|
return declaration.params.size();
|
||||||
|
|
|
@ -18,7 +18,7 @@ class LoxInstance {
|
||||||
|
|
||||||
LoxFunction method = klass.findMethod(name.lexeme);
|
LoxFunction method = klass.findMethod(name.lexeme);
|
||||||
if (method != null)
|
if (method != null)
|
||||||
return method;
|
return method.bind(this);
|
||||||
|
|
||||||
throw new RuntimeError(name, "Undefined proprety '" + name.lexeme + "'.");
|
throw new RuntimeError(name, "Undefined proprety '" + name.lexeme + "'.");
|
||||||
}
|
}
|
||||||
|
|
|
@ -355,6 +355,8 @@ class Parser {
|
||||||
return new Expr.Literal(previous().literal);
|
return new Expr.Literal(previous().literal);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (match(THIS)) return new Expr.This(previous());
|
||||||
|
|
||||||
if (match(IDENTIFIER)) {
|
if (match(IDENTIFIER)) {
|
||||||
return new Expr.Variable(previous());
|
return new Expr.Variable(previous());
|
||||||
}
|
}
|
||||||
|
|
|
@ -37,11 +37,16 @@ class Resolver implements Expr.Visitor<Void>, Stmt.Visitor<Void> {
|
||||||
declare(stmt.name);
|
declare(stmt.name);
|
||||||
define(stmt.name);
|
define(stmt.name);
|
||||||
|
|
||||||
|
beginScope();
|
||||||
|
scopes.peek().put("this", true);
|
||||||
|
|
||||||
for (Stmt.Function method : stmt.methods) {
|
for (Stmt.Function method : stmt.methods) {
|
||||||
FunctionType declaration = FunctionType.METHOD;
|
FunctionType declaration = FunctionType.METHOD;
|
||||||
resolveFunction(method, declaration);
|
resolveFunction(method, declaration);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
endScope();
|
||||||
|
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -154,6 +159,12 @@ class Resolver implements Expr.Visitor<Void>, Stmt.Visitor<Void> {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Void visitThisExpr(Expr.This expr) {
|
||||||
|
resolveLocal(expr, expr.keyword);
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Void visitLogicalExpr(Expr.Logical expr) {
|
public Void visitLogicalExpr(Expr.Logical expr) {
|
||||||
resolve(expr.left);
|
resolve(expr.left);
|
||||||
|
|
|
@ -19,7 +19,7 @@ public class GenerateAst {
|
||||||
"Call : Expr callee, Token paren, List<Expr> arguments", "Get : Expr object, Token name",
|
"Call : Expr callee, Token paren, List<Expr> arguments", "Get : Expr object, Token name",
|
||||||
"Grouping : Expr expression", "Literal : Object value",
|
"Grouping : Expr expression", "Literal : Object value",
|
||||||
"Logical : Expr left, Token operator, Expr right", "Set : Expr object, Token name, Expr value",
|
"Logical : Expr left, Token operator, Expr right", "Set : Expr object, Token name, Expr value",
|
||||||
"Unary : Token operator, Expr right", "Variable : Token name"));
|
"This : Token keyword", "Unary : Token operator, Expr right", "Variable : Token name"));
|
||||||
defineAst(outputDir, "Stmt",
|
defineAst(outputDir, "Stmt",
|
||||||
Arrays.asList("Block : List<Stmt> statements", "Class : Token name, List<Stmt.Function> methods",
|
Arrays.asList("Block : List<Stmt> statements", "Class : Token name, List<Stmt.Function> methods",
|
||||||
"Expression : Expr expression", "Function : Token name, List<Token> params, List<Stmt> body",
|
"Expression : Expr expression", "Function : Token name, List<Token> params, List<Stmt> body",
|
||||||
|
|
Loading…
Reference in a new issue