srctree

Robin Linden parent f4ab2d12 e193b0ef
js: Support BinaryExpression AST nodes

inlinesplit
js/ast.h added: 44, removed: 2, total 42
@@ -5,6 +5,7 @@
#ifndef JS_AST_H_
#define JS_AST_H_
 
#include <cstdlib>
#include <map>
#include <memory>
#include <optional>
@@ -70,6 +71,36 @@ private:
Value value_;
};
 
// TODO(robinlinden): Support more operators.
enum class BinaryOperator {
Minus,
Plus,
};
 
class BinaryExpression : public Expression {
public:
BinaryExpression(BinaryOperator op, std::unique_ptr<Expression> left, std::unique_ptr<Expression> right)
: op_{op}, left_{std::move(left)}, right_{std::move(right)} {}
 
// TODO(robinlinden): Support values that aren't doubles.
Value execute(Context &ctx) const override {
auto lhs = left_->execute(ctx);
auto rhs = right_->execute(ctx);
switch (op_) {
case BinaryOperator::Plus:
return Value{std::get<double>(lhs.value()) + std::get<double>(rhs.value())};
case BinaryOperator::Minus:
return Value{std::get<double>(lhs.value()) - std::get<double>(rhs.value())};
}
std::abort();
}
 
private:
BinaryOperator op_{};
std::unique_ptr<Expression> left_;
std::unique_ptr<Expression> right_;
};
 
class Program : public Node {
public:
Value execute(Context &ctx) const override {
 
js/ast_test.cpp added: 44, removed: 2, total 42
@@ -38,5 +38,16 @@ int main() {
expect_eq(ctx, Context{.variables = {{"a", Value{1.}}}});
});
 
etest::test("binary expression", [] {
auto plus_expr = BinaryExpression{
BinaryOperator::Plus, std::make_unique<Literal>(Value{11.}), std::make_unique<Literal>(Value{31.})};
Context ctx;
expect_eq(plus_expr.execute(ctx), Value{42.});
 
auto minus_expr = BinaryExpression{
BinaryOperator::Minus, std::make_unique<Literal>(Value{11.}), std::make_unique<Literal>(Value{31.})};
expect_eq(minus_expr.execute(ctx), Value{-20.});
});
 
return etest::run_all_tests();
}