]> Repositories - zlox.git/blob - src/ast_printer.zig
Rename error functions
[zlox.git] / src / ast_printer.zig
1 const std = @import("std");
2 const Allocator = std.mem.Allocator;
3 const Expr = @import("expr.zig").Expr;
4 const Token = @import("Token.zig");
5
6 pub fn print(allocator: Allocator, expr: *const Expr) Allocator.Error![]const u8 {
7     return switch (expr.*) {
8         .binary => |binary| try parenthesize(allocator, binary.operator.lexeme, &.{ binary.left, binary.right }),
9         .grouping => |grouping| try parenthesize(allocator, "group", &.{grouping.expression}),
10         .literal => |literal| switch (literal.value) {
11             .nil => try allocator.dupe(u8, "nil"),
12             .boolean => |boolean| try std.fmt.allocPrint(allocator, "{}", .{boolean}),
13             .string => |string| try allocator.dupe(u8, string),
14             .number => |number| try std.fmt.allocPrint(allocator, "{}", .{number}),
15         },
16         .unary => |unary| try parenthesize(allocator, unary.operator.lexeme, &.{unary.right}),
17     };
18 }
19
20 fn parenthesize(allocator: Allocator, name: []const u8, exprs: []const *const Expr) ![]const u8 {
21     var builder: std.ArrayList(u8) = .empty;
22
23     try builder.append(allocator, '(');
24     try builder.appendSlice(allocator, name);
25     for (exprs) |expr| {
26         try builder.append(allocator, ' ');
27         const printed = try print(allocator, expr);
28         defer allocator.free(printed);
29         try builder.appendSlice(allocator, printed);
30     }
31     try builder.append(allocator, ')');
32
33     return try builder.toOwnedSlice(allocator);
34 }