const std = @import("std"); const print = std.debug.print; const assert = std.debug.assert; const mem = std.mem; const fin = mem.trim(u8, @embedFile("./input.txt"), &std.ascii.whitespace); const digits_p1 = [_]u8{ '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', }; const digits_p2 = [_][]const u8{ "0", "zero", "1", "one", "2", "two", "3", "three", "4", "four", "5", "five", "6", "six", "7", "seven", "8", "eight", "9", "nine", }; pub fn part1(comptime T: type, input: T) void { var ans: u64 = 0; var it = input; while (it.next()) |line| { const first = line[mem.indexOfAny(u8, line, &digits_p1) orelse continue] - '0'; const last = line[mem.lastIndexOfAny(u8, line, &digits_p1) orelse continue] - '0'; const n = 10 * first + last; ans += n; } print("{d}\n", .{ans}); } pub fn part2(comptime T: type, input: T) void { var ans: u64 = 0; var it = input; while (it.next()) |line| { var first: u64 = 0; var last: u64 = 0; var first_idx: i64 = 10000000; var last_idx: i64 = -1; for (digits_p2, 0..) |d, i| { if (mem.indexOf(u8, line, d)) |t| { const fi: i64 = @bitCast(t); if (fi < first_idx) { first_idx = fi; first = i / 2; } } if (mem.lastIndexOf(u8, line, d)) |t| { const li: i64 = @bitCast(t); if (li > last_idx) { last_idx = li; last = i / 2; } } } const n = 10 * first + last; ans += n; } print("{d}\n", .{ans}); } pub fn main() !void { var gpa = std.heap.GeneralPurposeAllocator(.{}){}; defer _ = gpa.deinit(); var alloc = gpa.allocator(); _ = alloc; const input = mem.splitScalar(u8, fin, '\n'); part1(@TypeOf(input), input); part2(@TypeOf(input), input); }