2018 day 18 Done
This commit is contained in:
parent
3f65da791c
commit
1f6e1c932c
202
2018/day18/day18.go
Normal file
202
2018/day18/day18.go
Normal file
@ -0,0 +1,202 @@
|
||||
package main
|
||||
|
||||
import (
|
||||
"bufio"
|
||||
"fmt"
|
||||
"os"
|
||||
"time"
|
||||
)
|
||||
|
||||
const (
|
||||
DIR_N = -1i
|
||||
DIR_NE = 1 - 1i
|
||||
DIR_E = 1
|
||||
DIR_SE = 1 + 1i
|
||||
DIR_S = 1i
|
||||
DIR_SW = -1 + 1i
|
||||
DIR_W = -1
|
||||
DIR_NW = -1 - 1i
|
||||
|
||||
CLEAR_SCREEN = "\033[H\033[2J"
|
||||
)
|
||||
|
||||
var scan []byte
|
||||
var next []byte
|
||||
var prevScans [][]byte
|
||||
var width, height int
|
||||
|
||||
func main() {
|
||||
stdinToByteSlice()
|
||||
part1()
|
||||
part2()
|
||||
}
|
||||
|
||||
func part1() {
|
||||
printScan()
|
||||
for i := 0; i < 10; i++ {
|
||||
fmt.Print(CLEAR_SCREEN)
|
||||
scan = tickToNext()
|
||||
printScan()
|
||||
time.Sleep(time.Millisecond * 250)
|
||||
}
|
||||
var ttlOpen, ttlTrees, ttlLmbr int
|
||||
for i := range scan {
|
||||
switch getByte(getPosFromInt(i)) {
|
||||
case '.':
|
||||
ttlOpen++
|
||||
case '|':
|
||||
ttlTrees++
|
||||
case '#':
|
||||
ttlLmbr++
|
||||
}
|
||||
}
|
||||
_ = ttlOpen
|
||||
fmt.Println("= Part 1 =")
|
||||
fmt.Println(ttlTrees * ttlLmbr)
|
||||
}
|
||||
|
||||
// 191080?
|
||||
func part2() {
|
||||
var isDupe bool
|
||||
var i int
|
||||
target := 1000000000
|
||||
for i = 0; i < target; i++ {
|
||||
//fmt.Print(CLEAR_SCREEN, target)
|
||||
next := tickToNext()
|
||||
if isDupe, prevScans = checkDuplicateState(next, prevScans); isDupe {
|
||||
i++
|
||||
scan = next
|
||||
break
|
||||
}
|
||||
prevScans = append(prevScans, next)
|
||||
scan = next
|
||||
}
|
||||
// We need to find the state after `target` increments
|
||||
scan = prevScans[(target-i)%len(prevScans)]
|
||||
var ttlOpen, ttlTrees, ttlLmbr int
|
||||
for i := range scan {
|
||||
switch getByte(getPosFromInt(i)) {
|
||||
case '.':
|
||||
ttlOpen++
|
||||
case '|':
|
||||
ttlTrees++
|
||||
case '#':
|
||||
ttlLmbr++
|
||||
}
|
||||
}
|
||||
_ = ttlOpen
|
||||
fmt.Println("= Part 2 =")
|
||||
fmt.Println(ttlTrees * ttlLmbr)
|
||||
}
|
||||
|
||||
// checkDuplicateState returns the slice of prev that has all remaining available states
|
||||
func checkDuplicateState(s []byte, prev [][]byte) (bool, [][]byte) {
|
||||
for i, v := range prev {
|
||||
if areasAreEqual(s, v) {
|
||||
return true, prev[i:]
|
||||
}
|
||||
}
|
||||
return false, prev
|
||||
}
|
||||
|
||||
func areasAreEqual(a1, a2 []byte) bool {
|
||||
for i := range a1 {
|
||||
if a1[i] != a2[i] {
|
||||
return false
|
||||
}
|
||||
}
|
||||
return true
|
||||
}
|
||||
|
||||
func tickToNext() []byte {
|
||||
var ret []byte
|
||||
for i := 0; i < len(scan); i++ {
|
||||
c := getPosFromInt(i)
|
||||
_, sTree, sLmbr := getSurroundingCounts(c)
|
||||
b := getByte(c)
|
||||
switch b {
|
||||
case '.':
|
||||
if sTree >= 3 {
|
||||
ret = append(ret, '|')
|
||||
} else {
|
||||
ret = append(ret, '.')
|
||||
}
|
||||
case '|':
|
||||
if sLmbr >= 3 {
|
||||
ret = append(ret, '#')
|
||||
} else {
|
||||
ret = append(ret, '|')
|
||||
}
|
||||
case '#':
|
||||
if sLmbr > 0 && sTree > 0 {
|
||||
ret = append(ret, '#')
|
||||
} else {
|
||||
ret = append(ret, '.')
|
||||
}
|
||||
}
|
||||
}
|
||||
return ret
|
||||
}
|
||||
|
||||
// getSurroundingCounts takes a pos and returns:
|
||||
// Number of open areas
|
||||
// Number of trees
|
||||
// Number of lumberyards
|
||||
// Surrounding that spot
|
||||
func getSurroundingCounts(c complex64) (int, int, int) {
|
||||
var sOpen, sTree, sLmbr int
|
||||
for _, v := range []complex64{DIR_NW, DIR_N, DIR_NE, DIR_W, DIR_E, DIR_SW, DIR_S, DIR_SE} {
|
||||
switch getByte(c + v) {
|
||||
case '.':
|
||||
sOpen++
|
||||
case '|':
|
||||
sTree++
|
||||
case '#':
|
||||
sLmbr++
|
||||
}
|
||||
}
|
||||
return sOpen, sTree, sLmbr
|
||||
}
|
||||
|
||||
func printScan() {
|
||||
for i := 0; i < len(scan)/width; i++ {
|
||||
fmt.Println(string(scan[i*width : (i+1)*width]))
|
||||
}
|
||||
}
|
||||
|
||||
// getByte pulls a byte from the given position in the scan
|
||||
func getByte(pos complex64) byte {
|
||||
//idx := int(real(pos)) + int(imag(pos))*width
|
||||
if int(real(pos)) < 0 || int(imag(pos)) < 0 || int(real(pos)) >= width || int(imag(pos)) >= height {
|
||||
return 0
|
||||
}
|
||||
return scan[int(real(pos))+int(imag(pos))*width]
|
||||
}
|
||||
|
||||
func getPosComplex(x, y int) complex64 {
|
||||
return complex(float32(x), float32(y))
|
||||
}
|
||||
|
||||
func getPosFromInt(i int) complex64 {
|
||||
return complex(float32(i%width), float32(i/width))
|
||||
}
|
||||
|
||||
func getIdxFromPos(pos complex64) int {
|
||||
return int(real(pos)) + int(imag(pos))*width
|
||||
}
|
||||
|
||||
func getCoordString(p complex64) string {
|
||||
return fmt.Sprintf("(%d,%d [%d])", int(real(p)), int(imag(p)), getIdxFromPos(p))
|
||||
}
|
||||
|
||||
func stdinToByteSlice() {
|
||||
scanner := bufio.NewScanner(os.Stdin)
|
||||
for scanner.Scan() {
|
||||
s := scanner.Bytes()
|
||||
if width == 0 {
|
||||
width = len(s)
|
||||
}
|
||||
scan = append(scan, s...)
|
||||
height++
|
||||
}
|
||||
}
|
50
2018/day18/input
Normal file
50
2018/day18/input
Normal file
@ -0,0 +1,50 @@
|
||||
.#|#.##....#|....|.#.#.|||.#.|....||....|...|..#..
|
||||
..|#||.|#..|...|#|..#...|#...#..#..|.....||..#.|#.
|
||||
#|||#..||.....||.#................|..#.##|.#...#.|
|
||||
|#..#.|...##...#..#|#|#..|#.#...|....#..#...##....
|
||||
.###.........|.||#...#|.|#.||||#..|...||....#..#..
|
||||
###.|..|#|...|..||..##.....|..#.|.#.............|.
|
||||
..|.|.||.#....|...|....#|.........##||..#||..|.##.
|
||||
#||#|...#|..|.|.||#...#|...|#.......|...#.....|...
|
||||
....||.....|.|.....#...|.......|...|..|...|......|
|
||||
#......#..#|#|..|....#.|.|.#...#.#.|..#.|.....#.#.
|
||||
.|#...|...........#|.#....#.#...#.|..|...|....|.|.
|
||||
..||.#.|...||#|....#.#..||#..#...#|..#..|..#|.....
|
||||
|..|.|..#...|.....#.|..|#.||..#|.|.||#|#..|#...##|
|
||||
..|..|#......||##..|........#.|...#.|.|#.#...||..#
|
||||
#.|...#.||#..|.|..|..|.#....|.||....|.|....#....#.
|
||||
#||.|.#..#..|...#....##|#..#...#.#...|.#...#.....#
|
||||
#.|.##.|##..#.##|##........#.|...#...|..#|.#|#|...
|
||||
.|#|....|.#...#..|||.#.||..#||.||.|..#.|....|..##.
|
||||
|.#.||#|.##.|.||.....#...#.#..###|.#......||#|....
|
||||
.|.#..|#||......|##..##.#|..#|.|#.|.|#......|#.|#.
|
||||
#..|........|||..|###..|#..|||#.|.|.....#|..|...|#
|
||||
..####||#......|#||..###.|...|....#..|.#|.||....||
|
||||
|##.......|||..........|..||.#.|#.......##...|...|
|
||||
|.......#......####|#|....#....|......#.|#.###...#
|
||||
#|.#.|||...|..|.....#....|...|......|#|#|......||.
|
||||
...#.|......#..||||.#|.....|.|.|||.|.|.|#|.#...#.#
|
||||
#.#.##.|.#|.|...|...|...#|...#.|#..|..##.|....#..|
|
||||
|...#.......#....#....#.#....#.#|.|#||.|.|.|#...#.
|
||||
#..|.||..|.#..|.#.....#|##.|.|....|....||.......|.
|
||||
..||.#..|#|.###....#.#|..#|.#..........#...|...#|.
|
||||
|#||.|.#..|....|....#.#||#.|......#..|#.#.|||||#|.
|
||||
.|#.|#.##.....#.|.#.....|....|.#..#.#..|#.#.....|.
|
||||
#.||.#.......|..|......|#||.|..#....#...|...|...|.
|
||||
|.....#.|.....#||.....##...#.#...||.|..#........|.
|
||||
||#..|.##.#...........#..|..|.|..#....|...#..||.#.
|
||||
..||.##.##.|.||......#...|.#.#.#..#.#...##.#.|.#..
|
||||
.|.#......#|#||.|.#|......||.#.|.|..|....#...||...
|
||||
....|.##.....|#|####.#..#..#|.....|.#.#|......|...
|
||||
...#..|......#....|#.#...|...|.#.#.......#.#.##..#
|
||||
.|||#.||||...|..|#||.|.#|#||..|..#..|..|..#||.....
|
||||
.....|..#..|#|.||.#||.||......|||..|..#|.|##......
|
||||
.#...#|..#..|||..||.|..|.#.#.......||..|...|.|....
|
||||
.##.||..|..||.|.......#.|||.|.|..|.#.#..|.||.|#|||
|
||||
.|..##|..#.#|#|....|.#.#.#|#.#|.##|........###...#
|
||||
..#..|#|...#.........#.#.####..#.#..#..#||#|...#|#
|
||||
#.|...|.......|.#.#..#.|#..#|#|..#..|.....|..|...|
|
||||
.##.|..#.....|...#..|#..|.|.#..##.#.|..#.|..|.##..
|
||||
....|..|.|..||....|...|.....#..|.|.....|.#|......#
|
||||
...##.|#..#..|.#|.##....|.#...||#|.....#...##.#|..
|
||||
.|....##.....||...#.#.....#|#...#...#|.|..#.#.#.##
|
203
2018/day18/problem
Normal file
203
2018/day18/problem
Normal file
@ -0,0 +1,203 @@
|
||||
Advent of Code
|
||||
|
||||
--- Day 18: Settlers of The North Pole ---
|
||||
|
||||
On the outskirts of the North Pole base construction project, many Elves are collecting lumber.
|
||||
|
||||
The lumber collection area is 50 acres by 50 acres; each acre can be either open ground (.), trees (|), or a
|
||||
lumberyard (#). You take a scan of the area (your puzzle input).
|
||||
|
||||
Strange magic is at work here: each minute, the landscape looks entirely different. In exactly one minute, an
|
||||
open acre can fill with trees, a wooded acre can be converted to a lumberyard, or a lumberyard can be cleared
|
||||
to open ground (the lumber having been sent to other projects).
|
||||
|
||||
The change to each acre is based entirely on the contents of that acre as well as the number of open, wooded,
|
||||
or lumberyard acres adjacent to it at the start of each minute. Here, "adjacent" means any of the eight acres
|
||||
surrounding that acre. (Acres on the edges of the lumber collection area might have fewer than eight adjacent
|
||||
acres; the missing acres aren't counted.)
|
||||
|
||||
In particular:
|
||||
|
||||
• An open acre will become filled with trees if three or more adjacent acres contained trees. Otherwise,
|
||||
nothing happens.
|
||||
• An acre filled with trees will become a lumberyard if three or more adjacent acres were lumberyards.
|
||||
Otherwise, nothing happens.
|
||||
• An acre containing a lumberyard will remain a lumberyard if it was adjacent to at least one other
|
||||
lumberyard and at least one acre containing trees. Otherwise, it becomes open.
|
||||
|
||||
These changes happen across all acres simultaneously, each of them using the state of all acres at the
|
||||
beginning of the minute and changing to their new form by the end of that same minute. Changes that happen
|
||||
during the minute don't affect each other.
|
||||
|
||||
For example, suppose the lumber collection area is instead only 10 by 10 acres with this initial
|
||||
configuration:
|
||||
|
||||
Initial state:
|
||||
.#.#...|#.
|
||||
.....#|##|
|
||||
.|..|...#.
|
||||
..|#.....#
|
||||
#.#|||#|#|
|
||||
...#.||...
|
||||
.|....|...
|
||||
||...#|.#|
|
||||
|.||||..|.
|
||||
...#.|..|.
|
||||
|
||||
After 1 minute:
|
||||
.......##.
|
||||
......|###
|
||||
.|..|...#.
|
||||
..|#||...#
|
||||
..##||.|#|
|
||||
...#||||..
|
||||
||...|||..
|
||||
|||||.||.|
|
||||
||||||||||
|
||||
....||..|.
|
||||
|
||||
After 2 minutes:
|
||||
.......#..
|
||||
......|#..
|
||||
.|.|||....
|
||||
..##|||..#
|
||||
..###|||#|
|
||||
...#|||||.
|
||||
|||||||||.
|
||||
||||||||||
|
||||
||||||||||
|
||||
.|||||||||
|
||||
|
||||
After 3 minutes:
|
||||
.......#..
|
||||
....|||#..
|
||||
.|.||||...
|
||||
..###|||.#
|
||||
...##|||#|
|
||||
.||##|||||
|
||||
||||||||||
|
||||
||||||||||
|
||||
||||||||||
|
||||
||||||||||
|
||||
|
||||
After 4 minutes:
|
||||
.....|.#..
|
||||
...||||#..
|
||||
.|.#||||..
|
||||
..###||||#
|
||||
...###||#|
|
||||
|||##|||||
|
||||
||||||||||
|
||||
||||||||||
|
||||
||||||||||
|
||||
||||||||||
|
||||
|
||||
After 5 minutes:
|
||||
....|||#..
|
||||
...||||#..
|
||||
.|.##||||.
|
||||
..####|||#
|
||||
.|.###||#|
|
||||
|||###||||
|
||||
||||||||||
|
||||
||||||||||
|
||||
||||||||||
|
||||
||||||||||
|
||||
|
||||
After 6 minutes:
|
||||
...||||#..
|
||||
...||||#..
|
||||
.|.###|||.
|
||||
..#.##|||#
|
||||
|||#.##|#|
|
||||
|||###||||
|
||||
||||#|||||
|
||||
||||||||||
|
||||
||||||||||
|
||||
||||||||||
|
||||
|
||||
After 7 minutes:
|
||||
...||||#..
|
||||
..||#|##..
|
||||
.|.####||.
|
||||
||#..##||#
|
||||
||##.##|#|
|
||||
|||####|||
|
||||
|||###||||
|
||||
||||||||||
|
||||
||||||||||
|
||||
||||||||||
|
||||
|
||||
After 8 minutes:
|
||||
..||||##..
|
||||
..|#####..
|
||||
|||#####|.
|
||||
||#...##|#
|
||||
||##..###|
|
||||
||##.###||
|
||||
|||####|||
|
||||
||||#|||||
|
||||
||||||||||
|
||||
||||||||||
|
||||
|
||||
After 9 minutes:
|
||||
..||###...
|
||||
.||#####..
|
||||
||##...##.
|
||||
||#....###
|
||||
|##....##|
|
||||
||##..###|
|
||||
||######||
|
||||
|||###||||
|
||||
||||||||||
|
||||
||||||||||
|
||||
|
||||
After 10 minutes:
|
||||
.||##.....
|
||||
||###.....
|
||||
||##......
|
||||
|##.....##
|
||||
|##.....##
|
||||
|##....##|
|
||||
||##.####|
|
||||
||#####|||
|
||||
||||#|||||
|
||||
||||||||||
|
||||
|
||||
After 10 minutes, there are 37 wooded acres and 31 lumberyards. Multiplying the number of wooded acres by the
|
||||
number of lumberyards gives the total resource value after ten minutes: 37 * 31 = 1147.
|
||||
|
||||
What will the total resource value of the lumber collection area be after 10 minutes?
|
||||
|
||||
Your puzzle answer was 644640.
|
||||
|
||||
--- Part Two ---
|
||||
|
||||
This important natural resource will need to last for at least thousands of years. Are the Elves collecting
|
||||
this lumber sustainably?
|
||||
|
||||
What will the total resource value of the lumber collection area be after 1000000000 minutes?
|
||||
|
||||
Your puzzle answer was 191080.
|
||||
|
||||
Both parts of this puzzle are complete! They provide two gold stars: **
|
||||
|
||||
References
|
||||
|
||||
Visible links
|
||||
. https://adventofcode.com/
|
||||
. https://adventofcode.com/2018/about
|
||||
. https://adventofcode.com/2018/events
|
||||
. https://adventofcode.com/2018/settings
|
||||
. https://adventofcode.com/2018/auth/logout
|
||||
. Advent of Code Supporter
|
||||
https://adventofcode.com/2018/support
|
||||
. https://adventofcode.com/2018
|
||||
. https://adventofcode.com/2018
|
||||
. https://adventofcode.com/2018/support
|
||||
. https://adventofcode.com/2018/sponsors
|
||||
. https://adventofcode.com/2018/leaderboard
|
||||
. https://adventofcode.com/2018/stats
|
||||
. https://adventofcode.com/2018/sponsors
|
||||
. https://adventofcode.com/2018
|
||||
. https://adventofcode.com/2018/day/18/input
|
10
2018/day18/testinput
Normal file
10
2018/day18/testinput
Normal file
@ -0,0 +1,10 @@
|
||||
.#.#...|#.
|
||||
.....#|##|
|
||||
.|..|...#.
|
||||
..|#.....#
|
||||
#.#|||#|#|
|
||||
...#.||...
|
||||
.|....|...
|
||||
||...#|.#|
|
||||
|.||||..|.
|
||||
...#.|..|.
|
Loading…
Reference in New Issue
Block a user