No field or member function named `init` in `scanner`

pub const Scanner = struct {
    start: usize = 0,
    current: usize = 0,
    line: usize = 1,

    source: []u8,
    tokens: std.ArrayList(Token.Token),
    
    const keywords = std.StaticStringMap(Token.TokenType).initComptime(.{
        .{ "and", .AND },
        // etc
    });

For initialization, you can initialize in place:

var scanner = Scanner.Scanner{
    .source = src,
    .tokens = std.ArrayList(Token.Token).init(allocator),
}

but the convention is to create an init function to make initializing non-trivial structs more convenient:

    pub fn init(allocator: std.mem.Allocator, src: []const u8) Scanner {
        return .{
            .source = src,
            .tokens = std.ArrayList(Token.Token).init(allocator),
        };
    }

so then you’d just call

var scanner = Scanner.Scanner.init(allocator, src);

On the Scanner.Scanner thing, you might be interested in taking advantage of the fact that in Zig, files are structs, so you can create a Scanner.zig like so:

const Scanner = @This();

start: usize = 0,
current: usize = 0,
line: usize = 1,

source: []u8,
tokens: std.ArrayList(Token.Token),

pub fn init(allocator: std.mem.Allocator, src: []const u8) Scanner {
    return .{
        .source = src,
        .tokens = std.ArrayList(Token.Token).init(allocator),
    };
}

and then use it like this:

const Scanner = @import("Scanner.zig");

pub fn main() !void {
    // ...

    var scanner = Scanner.init(allocator, src);
    defer scanner.deinit();
}
1 Like