diff --git a/tree.hpp b/tree.hpp new file mode 100644 index 0000000..03d445f --- /dev/null +++ b/tree.hpp @@ -0,0 +1,94 @@ +#pragma once +#include +#include + +enum class binop { + plus, + minus, + times, + divide, + land, + lor, + eq, + neq, + lt, + lte, + gt, + gte +}; + +enum class unop { + lnot +}; + +struct expr { + virtual ~expr() = default; +}; + +typedef std::unique_ptr expr_ptr; + +struct expr_binop : expr { + binop op; + expr_ptr left; + expr_ptr right; + + expr_binop(binop nop, expr_ptr l, expr_ptr r) : + op(nop), left(std::move(l)), right(std::move(r)) {} +}; + +struct expr_unop : expr { + unop op; + expr_ptr child; + + expr_unop(unop nop, expr_ptr c) : + op(nop), child(std::move(c)) {} +}; + +struct expr_assign : expr { + std::string var; + expr_ptr child; + + expr_assign(std::string v, expr_ptr c) : + var(std::move(v)), child(std::move(c)) {} +}; + +template +expr_ptr make_expr(Ts&& ... ts) { + return expr_ptr(new T(std::move(ts)...)); +} + +struct stmt { + virtual ~stmt() = default; +}; + +typedef std::unique_ptr stmt_ptr; + +struct stmt_block : stmt { + std::vector children; +}; + +struct stmt_if : stmt { + expr_ptr cond; + stmt_ptr then; + stmt_ptr els; + + stmt_if(expr_ptr c, stmt_ptr t, stmt_ptr e = nullptr) : + cond(std::move(c)), then(std::move(t)), els(std::move(e)) {} +}; + +struct stmt_while : stmt { + expr_ptr cond; + stmt_ptr body; + + stmt_while(expr_ptr c, stmt_ptr b) + : cond(std::move(c)), body(std::move(b)) {} +}; + +struct stmt_break : stmt { + +}; + +template +stmt_ptr make_stmt(Ts&& ... ts) { + return stmt_ptr(new T(std::move(ts)...)); +}