Also add typeprof for the LSP

FossilOrigin-Name: 5083d12e51edc11e5c25174af3fb0276b6a1952a28184b8f43079b6907e2caf5
private
alpha 2 years ago
parent b879ae44ff
commit ce32eea3d9

@ -7,3 +7,4 @@ git_source(:github) {|repo_name| "https://github.com/#{repo_name}" }
gem "minitest"
gem "pry"
gem "rake"
gem "typeprof"

@ -8,6 +8,9 @@ GEM
coderay (~> 1.1)
method_source (~> 1.0)
rake (13.0.6)
rbs (2.6.0)
typeprof (0.21.3)
rbs (>= 1.8.1)
PLATFORMS
arm64-darwin-21
@ -16,6 +19,7 @@ DEPENDENCIES
minitest
pry
rake
typeprof
BUNDLED WITH
2.3.18

@ -22,6 +22,10 @@ module Lox
parenthesize("assign #{expr.name.lexeme}", expr.value)
end
def visit_block(expr)
parenthesize("block", *expr.stmts)
end
private
def parenthesize(name, *exprs)

@ -11,11 +11,28 @@ module Lox
# we're going to do it in the runner instead.
def interpret(stmts)
stmts.each do |stmt|
evaluate(stmt)
execute(stmt)
end
end
def evaluate(stmt) = stmt.accept(self)
def evaluate(expr) = expr.accept(self)
def execute(stmt) = stmt.accept(self)
def visit_block(stmt)
execute_block(stmt.stmts, Environment.new(@env))
nil
end
def execute_block(stmts, env)
prev_env = @env
@env = env
stmts.each do |stmt|
execute(stmt)
end
ensure
@env = prev_env
end
def visit_expr(expr)
evaluate(expr.expr)

@ -38,6 +38,7 @@ module Lox
def statement
return print if match?(:PRINT)
return Stmt::Block.new(block) if match?(:LEFT_BRACE)
expression_stmt
end
@ -54,6 +55,15 @@ module Lox
Stmt::Expr.new(value)
end
def block
statements = []
until check?(:RIGHT_BRACE) || eot?
statements << declaration
end
consume!(:RIGHT_BRACE, "Expect '}' after block.")
statements
end
def assignment
expr = equality

@ -2,6 +2,10 @@ require_relative "visitable"
module Lox
module Stmt
Block = Struct.new(:stmts) do
include Visitable
end
Expr = Struct.new(:expr) do
include Visitable
end

@ -116,6 +116,40 @@ class TestInterpreter < Lox::Test
SRC
end
def test_block
assert_interpreted <<~EXPECTED.chomp, <<~SRC
inner a
outer b
global c
outer a
outer b
global c
global a
global b
global c
EXPECTED
var a = "global a";
var b = "global b";
var c = "global c";
{
var a = "outer a";
var b = "outer b";
{
var a = "inner a";
print a;
print b;
print c;
}
print a;
print b;
print c;
}
print a;
print b;
print c;
SRC
end
private
def assert_interpreted(expected, src)

@ -60,6 +60,15 @@ class TestParser < Lox::Test
assert_parsed "(print (assign foo 42.0))", :declaration, "print foo = 42.0;"
end
def test_block
assert_parsed "(block (var foo bar) (print (var foo)))", :statement, <<~SRC
{
var foo = "bar";
print foo;
}
SRC
end
private
def assert_parsed(expected, name, src)

Loading…
Cancel
Save