[jlox] Interpret superclasses

This commit is contained in:
ctsk
2022-10-11 12:58:28 +02:00
parent e68b3036f7
commit f0b55491d8
2 changed files with 16 additions and 2 deletions

View File

@@ -80,6 +80,14 @@ public class Interpreter implements Expr.Visitor<Object>, Stmt.Visitor<Void> {
@Override @Override
public Void visitClassStmt(Stmt.Class stmt) { public Void visitClassStmt(Stmt.Class stmt) {
Object superclass = null;
if (stmt.superclass() != null) {
superclass = evaluate(stmt.superclass());
if (!(superclass instanceof LoxClass)) {
throw new RuntimeError(stmt.superclass().name(), "Superclass must be a class.");
}
}
environment.define(stmt.name().lexeme(), null); environment.define(stmt.name().lexeme(), null);
Map<String, LoxFunction> methods = new HashMap<>(); Map<String, LoxFunction> methods = new HashMap<>();
@@ -88,7 +96,7 @@ public class Interpreter implements Expr.Visitor<Object>, Stmt.Visitor<Void> {
methods.put(method.name().lexeme(), function); methods.put(method.name().lexeme(), function);
} }
LoxClass clazz = new LoxClass(stmt.name().lexeme(), methods); LoxClass clazz = new LoxClass(stmt.name().lexeme(), (LoxClass) superclass, methods);
environment.assign(stmt.name(), clazz); environment.assign(stmt.name(), clazz);
return null; return null;
} }

View File

@@ -5,10 +5,12 @@ import java.util.Map;
public class LoxClass implements LoxCallable { public class LoxClass implements LoxCallable {
final String name; final String name;
private final LoxClass superclass;
private final Map<String, LoxFunction> methods; private final Map<String, LoxFunction> methods;
LoxClass(String name, Map<String, LoxFunction> methods) { LoxClass(String name, LoxClass superclass, Map<String, LoxFunction> methods) {
this.name = name; this.name = name;
this.superclass = superclass;
this.methods = methods; this.methods = methods;
} }
@@ -39,6 +41,10 @@ public class LoxClass implements LoxCallable {
return methods.get(name); return methods.get(name);
} }
if (superclass != null) {
return superclass.findMethod(name);
}
return null; return null;
} }
} }