-
Notifications
You must be signed in to change notification settings - Fork 1
/
day-13.toit
84 lines (68 loc) · 1.85 KB
/
day-13.toit
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
import .file as file
import reader show BufferedReader
// Transparent paper-folding task.
main:
reader := BufferedReader
file.Stream.for_read "13.txt"
// We use a Set for the sheet of dots so that we don't have to know the size
// ahead of time, and dots that coincide will not cause duplicates.
sheet := Set
while line := reader.read_line:
if line == "": break
// Read line in format "12,34".
coords := (line.split ",").map: int.parse it
sheet.add
Coordinate coords[0] coords[1]
printed := false
while line := reader.read_line:
// Read line in format "fold along x=123".
at := int.parse line[13..]
if line[11] == 'x':
sheet = fold_x sheet at
else:
sheet = fold_y sheet at
if not printed:
print sheet.size
printed = true
// Find largest coordinates.
height := sheet.reduce --initial=0: | a b | max a (b.y + 1)
width := sheet.reduce --initial=0: | a b | max a (b.x + 1)
// Make a list of ByteArrays filled with space characters.
grid := List height:
ByteArray width: ' '
// Replace spaces with hashes at the points.
sheet.do: grid[it.y][it.x] = '#'
// Print the grid.
grid.do: print it.to_string
fold_y sheet/Set at/int -> Set:
result := {}
sheet.do:
if it.y == at:
throw "Fold on dot"
else if it.y < at:
result.add it
else:
result.add
Coordinate it.x (2 * at - it.y)
return result
fold_x sheet/Set at/int -> Set:
result := {}
sheet.do:
if it.x == at:
throw "Fold on dot"
else if it.x < at:
result.add it
else:
result.add
Coordinate (2 * at - it.x) it.y
return result
class Coordinate:
x /int
y /int
constructor .x .y:
hash_code -> int:
return x + y * 1000
operator == other -> bool:
return x == other.x and y == other.y
stringify -> string:
return "[$x,$y]"