package main
import "core:bytes"
import "core:fmt"
import "core:io"
import "core:os"
import "core:strings"
Input :: distinct struct {
raw_data: []byte,
lines: [dynamic]string,
}
Result1 :: distinct int
Result2 :: distinct int
// --- Input --- //
parse_input_file :: proc(filepath: string) -> Input {
input: Input
ok: bool
input.raw_data, ok = os.read_entire_file_from_filename(filepath)
if !ok {
panic("oh no, could not read file")
}
buf: bytes.Buffer
bytes.buffer_init(&buf, input.raw_data)
input.lines = make([dynamic]string, 0, 10)
line: string
err: io.Error
for ; err != .EOF; line, err = bytes.buffer_read_string(&buf, '\n') {
if line == "" || line == "\n" {
continue
}
append(&input.lines, line[:len(line) - 1])
}
return input
}
free_input :: proc(input: ^Input) {
delete(input.lines)
delete(input.raw_data)
}
// --- Input --- //
// --- Task 1 --- //
run_task1 :: proc(input: ^Input, debug: bool) -> Result1 {
result: Result1
for line, i in input.lines {
first, second := -1, -1
for char in line {
if char >= '0' && char <= '9' {
if first == -1 {
first = int(char - '0')
second = first
} else {
second = int(char - '0')
}
}
}
r := Result1((first * 10) + second)
if debug {
fmt.printf("%d: %d\n", i, r)
}
result += r
}
return result
}
print_result1 :: proc(result: ^Result1) {
fmt.printf("Task 1: %d\n", result^)
}
// --- Task 1 --- //
// --- Task 2 --- //
digits := []string{"one", "two", "three", "four", "five", "six", "seven", "eight", "nine"}
run_task2 :: proc(input: ^Input, debug: bool) -> Result2 {
result: Result2
for line, i in input.lines {
if debug {
fmt.printf("%d: %s\n", i, line)
}
first_index, first_value := -1, -1
second_index, second_value := -1, -1
for char, ci in line {
if char >= '0' && char <= '9' {
if first_index == -1 {
first_index = ci
first_value = int(char - '0')
second_index = first_index
second_value = first_value
} else {
second_index = ci
second_value = int(char - '0')
}
}
}
if debug {
fmt.printf("%d: %d, %d: %d\n", first_index, first_value, second_index, second_value)
}
for digit, digit_index in digits {
if di := strings.index(line, digit); di > -1 && (first_index < 0 || di < first_index) {
first_index = di
first_value = digit_index + 1
if debug {
fmt.printf("first match: %s %d -> %d\n", digit, digit_index, i)
}
}
if di := strings.last_index(line, digit); di > -1 && (second_index < 0 || di > second_index) {
second_index = di
second_value = digit_index + 1
if debug {
fmt.printf("second match: %s %d -> %d\n", digit, digit_index, i)
}
}
}
r := Result2((first_value * 10) + second_value)
if debug {
fmt.printf("%d: %d\n", i, r)
}
result += r
}
return result
}
print_result2 :: proc(result: ^Result2) {
fmt.printf("Task 2: %d\n", result^)
}
// --- Task 2 --- //