Compare commits
12 Commits
37ee3e99da
...
762e72744c
Author | SHA1 | Date |
---|---|---|
|
762e72744c | |
|
85dd9a31e3 | |
|
d4c162db33 | |
|
adcb2417ff | |
|
4d346a23db | |
|
6398a4d468 | |
|
42b587918e | |
|
c187a03076 | |
|
cdf5a38512 | |
|
3a43f90431 | |
|
7032666476 | |
|
65d6c13016 |
|
@ -0,0 +1,109 @@
|
||||||
|
package day11
|
||||||
|
|
||||||
|
import (
|
||||||
|
"fmt"
|
||||||
|
"log"
|
||||||
|
"os"
|
||||||
|
"strings"
|
||||||
|
)
|
||||||
|
|
||||||
|
func Run() int64 {
|
||||||
|
fmt.Println("hello day 11")
|
||||||
|
|
||||||
|
filename := "day11/input"
|
||||||
|
bytes, err := os.ReadFile(filename)
|
||||||
|
if err != nil {
|
||||||
|
panic(fmt.Sprint("cannot read file ", filename))
|
||||||
|
}
|
||||||
|
|
||||||
|
text := strings.TrimSpace( string(bytes) )
|
||||||
|
starCoords := make([]StarCoord, 0)
|
||||||
|
|
||||||
|
lines := strings.Split(text, "\n")
|
||||||
|
|
||||||
|
nonEmptyRows := make(map[int]any)
|
||||||
|
nonEmptyCols := make(map[int]any)
|
||||||
|
|
||||||
|
for rowNum, line := range lines {
|
||||||
|
for colNum, symb := range line {
|
||||||
|
if symb == '#' {
|
||||||
|
starCoords = append(starCoords, StarCoord{rowNum, colNum})
|
||||||
|
nonEmptyCols[colNum] = struct{}{}
|
||||||
|
nonEmptyRows[rowNum] = struct{}{}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
emptyRowsAbove := make([]int, len(lines))
|
||||||
|
emptyColsToTheLeft := make([]int, len(lines))
|
||||||
|
|
||||||
|
for rowNum, _ := range lines {
|
||||||
|
if rowNum > 0 {
|
||||||
|
emptyRowsAbove[rowNum] = emptyRowsAbove[rowNum-1]
|
||||||
|
}
|
||||||
|
_, isRowNonempty := nonEmptyRows[rowNum]
|
||||||
|
if !isRowNonempty {
|
||||||
|
emptyRowsAbove[rowNum] += 1
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
for colNum, _ := range lines[0] {
|
||||||
|
if colNum > 0 {
|
||||||
|
emptyColsToTheLeft[colNum] = emptyColsToTheLeft[colNum-1]
|
||||||
|
}
|
||||||
|
_, isColNonempty := nonEmptyCols[colNum]
|
||||||
|
if !isColNonempty {
|
||||||
|
emptyColsToTheLeft[colNum] += 1
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
var distanceSum int64
|
||||||
|
for i := 0; i < len(starCoords); i++ {
|
||||||
|
for j := i+1; j < len(starCoords); j++ {
|
||||||
|
// calc distance between stars i and j
|
||||||
|
starA := starCoords[i]
|
||||||
|
starB := starCoords[j]
|
||||||
|
|
||||||
|
maxRow := starA.Row
|
||||||
|
minRow := starB.Row
|
||||||
|
|
||||||
|
if maxRow < minRow {
|
||||||
|
maxRow, minRow = minRow, maxRow
|
||||||
|
}
|
||||||
|
|
||||||
|
var multiplier int64
|
||||||
|
multiplier = 1000000 - 1
|
||||||
|
|
||||||
|
emptyRowsBetween := int64(emptyRowsAbove[maxRow]) - int64(emptyRowsAbove[minRow])
|
||||||
|
|
||||||
|
rowDistance := int64(maxRow) - int64(minRow) + emptyRowsBetween*multiplier
|
||||||
|
|
||||||
|
maxCol := starA.Col
|
||||||
|
minCol := starB.Col
|
||||||
|
if maxCol < minCol {
|
||||||
|
maxCol, minCol = minCol, maxCol
|
||||||
|
}
|
||||||
|
|
||||||
|
emptyColsBetween := int64(emptyColsToTheLeft[maxCol]) - int64(emptyColsToTheLeft[minCol])
|
||||||
|
|
||||||
|
colDistance := int64(maxCol) - int64(minCol) + emptyColsBetween*multiplier
|
||||||
|
|
||||||
|
distance := rowDistance + colDistance
|
||||||
|
log.Printf("between stars %d %+v and %d %+v distance is %d. emptyColsBetween %d ; emptyRowsBetween %d\n", i, j, starA, starB, distance, emptyColsBetween, emptyRowsBetween)
|
||||||
|
distanceSum += int64(distance)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// oh, i have list of all stars, i can just iterate over them and
|
||||||
|
// only keep rowNums for which there are stars. yeah
|
||||||
|
|
||||||
|
fmt.Println(starCoords)
|
||||||
|
fmt.Println(emptyRowsAbove)
|
||||||
|
fmt.Println(emptyColsToTheLeft)
|
||||||
|
|
||||||
|
return distanceSum
|
||||||
|
}
|
||||||
|
|
||||||
|
type StarCoord struct {
|
||||||
|
Row, Col int
|
||||||
|
}
|
|
@ -0,0 +1,10 @@
|
||||||
|
...#......
|
||||||
|
.......#..
|
||||||
|
#.........
|
||||||
|
..........
|
||||||
|
......#...
|
||||||
|
.#........
|
||||||
|
.........#
|
||||||
|
..........
|
||||||
|
.......#..
|
||||||
|
#...#.....
|
|
@ -0,0 +1,140 @@
|
||||||
|
........................#...............................................#................................#................................#.
|
||||||
|
....#..............#......................#............#....................................................................#...............
|
||||||
|
................................#.............................................................#.............................................
|
||||||
|
.........#.....................................#...................#........................................................................
|
||||||
|
....................................................#.......................#..............................#................................
|
||||||
|
..#................................................................................................#................#......................#
|
||||||
|
.........................................................#.........................#.....#..................................................
|
||||||
|
..................................#.............................#...............................................#.............#.............
|
||||||
|
.......#.....#...........................#..............................................................#.............................#.....
|
||||||
|
......................#...............................#................................................................#....................
|
||||||
|
............................#.................#........................#.....................................#..............................
|
||||||
|
....#.................................#...............................................#.....................................................
|
||||||
|
...............#...........................................................#............................................................#...
|
||||||
|
..................................#...........................................................#...................#...........#.............
|
||||||
|
....................................................................................................................................#.......
|
||||||
|
................................................................#................#..........................#...............................
|
||||||
|
...#..............#........#.........#.............#........................................................................................
|
||||||
|
.........................................................#.............#.............#..............#...................#...................
|
||||||
|
........#...................................................................................................................................
|
||||||
|
..............................................................................................#.................................#........#..
|
||||||
|
....................#.......................................#.....................................................#.........................
|
||||||
|
#..............................#.......#......#...................................#......#..................................................
|
||||||
|
...........#.......................................#......................................................................#.................
|
||||||
|
.......................................................................................................................................#....
|
||||||
|
............................................................................................................................................
|
||||||
|
.........................#...................................#...............................#..............................................
|
||||||
|
..................................#.......................................................................#.............#...................
|
||||||
|
.........................................#...........................#...............................#.........#..........................#.
|
||||||
|
............#......#............................................#...............................#...................................#.......
|
||||||
|
.............................#.....................................................#........................................................
|
||||||
|
....#........................................#...............................#.................................................#............
|
||||||
|
......................#............................#.....#.........#........................................................................
|
||||||
|
.........................................................................................................#..................................
|
||||||
|
.......#........................#................................................#..........................................................
|
||||||
|
...............................................#..........................#................#..........................................#.....
|
||||||
|
.#................#.............................................................................................#......#....................
|
||||||
|
..............................................................................................................................#.............
|
||||||
|
..........................#........................#.............................................#..........................................
|
||||||
|
.............#..........................#............................................#..............................#.......................
|
||||||
|
........#..............................................#.....................#..........................#..................#................
|
||||||
|
............................................................#.....#..................................................................#......
|
||||||
|
....................#.........................#..........................#..................#...................#...........................
|
||||||
|
..............................#...................................................#................#........................................
|
||||||
|
.........................................#..............................................#..................................................#
|
||||||
|
.#........#.........................................#.....................................................#.....................#...........
|
||||||
|
.........................................................#.........................................................#........................
|
||||||
|
......#...........................#.........................................................................................................
|
||||||
|
................................................#........................................................................................#..
|
||||||
|
...................................................................#...............#........................................................
|
||||||
|
.....................#................................#..............................................................................#......
|
||||||
|
...........#................................................................................#.....#.........................................
|
||||||
|
....#........................#............................................#..............................................#..................
|
||||||
|
................#.......#........................................................#........................................................#.
|
||||||
|
#...................................................................................................................#.......................
|
||||||
|
....................#...................#..............#.................................#...................#..............................
|
||||||
|
.............#....................#.................................................#..................#...................#................
|
||||||
|
.................................................................................................................#.....................#....
|
||||||
|
................................................................................#...........................................................
|
||||||
|
.......................#.............#....................#.................................................................................
|
||||||
|
.......#.............................................................................................#..............#.......................
|
||||||
|
...................#.....................................................................................................................#..
|
||||||
|
......................................................#..................#.......................................................#..........
|
||||||
|
..........................#..................................................................#..............................................
|
||||||
|
............#.................................#.........................................#...................#............#..................
|
||||||
|
.....................#......................................#......................................................#..........#.............
|
||||||
|
.#.........................................................................#......#...................#.....................................
|
||||||
|
............................................................................................................................................
|
||||||
|
................................#...........................................................#...............................................
|
||||||
|
........................................#..........................#..................................................#.................#...
|
||||||
|
....#........................................#.....................................................#.............................#..........
|
||||||
|
..........................................................#.................................................................................
|
||||||
|
...............#............................................................................................................................
|
||||||
|
..........#............#............................#.............................#...........................................#......#......
|
||||||
|
....................................#........................................................#...............#..............................
|
||||||
|
...........................................#..............................#...............................................................#.
|
||||||
|
.#...........................#.......................................................................#......................................
|
||||||
|
.........................................................#...........#....................................#.................................
|
||||||
|
......#.......#...................#...........................#.......................#.........#..................#........................
|
||||||
|
............................................................................#.........................................................#.....
|
||||||
|
.....................#.........................................................................................#........#...................
|
||||||
|
..........................#.............................................#................#........................................#.........
|
||||||
|
............................................................................................................................................
|
||||||
|
....#.....#.....#..................................#.........#.....................#....................#...................................
|
||||||
|
........................................#.....................................................................................#.............
|
||||||
|
...............................................................................................#............................................
|
||||||
|
.......#........................#...........................................#............................................................#..
|
||||||
|
....................#......#....................#...........................................................................................
|
||||||
|
.........................................................#...........#..........#.............................#...........#.................
|
||||||
|
......................................................................................#.....................................................
|
||||||
|
....................................................................................................#................#..........#.....#.....
|
||||||
|
............#.........#.....................#...............#..............................................#................................
|
||||||
|
.......#............................#.......................................................................................................
|
||||||
|
.......................................................................#......................#................#...................#........
|
||||||
|
............................................................................................................................................
|
||||||
|
........................................................................................................................#...................
|
||||||
|
..........#..........#.......................#.........................................................................................#....
|
||||||
|
...................................................................#.................#...........#..........................................
|
||||||
|
........................................#................#..................................................................................
|
||||||
|
................#....................................................................................................#......................
|
||||||
|
............................................................................................................................................
|
||||||
|
.......#....................#.................................................................#...............#.........................#...
|
||||||
|
.................................#...........#.....#...........................................................................#............
|
||||||
|
...........#.......................................................#....................#...................................................
|
||||||
|
........................................#...............................................................................#...................
|
||||||
|
............................................................................................................................................
|
||||||
|
.....................................................................................................#......................................
|
||||||
|
................#.........................................#..................#................................................#.......#.....
|
||||||
|
....#................................#.............#...................................#.....................#.......#......................
|
||||||
|
.........................#......................................#...........................................................................
|
||||||
|
...........................................................................................#.......#........................................
|
||||||
|
..........#.....................#..............#........................#...................................................................
|
||||||
|
..#.........................................................................................................................................
|
||||||
|
....................#.....................................#.......................#.........................................................
|
||||||
|
..........................#.............#...............................................................................#.........#.........
|
||||||
|
......................................................................................#.....................................................
|
||||||
|
.....................................................................#..........................#...........................................
|
||||||
|
.......#.........#...........................................................#.......................#........#............#............#...
|
||||||
|
........................#....................................#..............................................................................
|
||||||
|
.......................................#............................................#....................#.........................#........
|
||||||
|
..............................................#....................................................................#........................
|
||||||
|
..............#..................#.....................................#..........................#.........................................
|
||||||
|
..........................................#..........#..........................#...........................................................
|
||||||
|
.....#......................................................................................#................#..............................
|
||||||
|
.....................#................................................................#.......................................#.............
|
||||||
|
.....................................................................#......................................................................
|
||||||
|
...........#.....#............................#.....................................................................................#.......
|
||||||
|
................................#.....#..........................#........#..........................................#....................#.
|
||||||
|
...........................#.................................................................#........#.......#.............................
|
||||||
|
#...........................................................................................................................................
|
||||||
|
........#........................................#...................................#......................................................
|
||||||
|
.............................................................................................................................#..............
|
||||||
|
.................................#..............................#........................#.........#........#...............................
|
||||||
|
............#.....#..........................#.......................#....................................................................#.
|
||||||
|
........................#........................................................#..........................................................
|
||||||
|
............................................................#..............#......................................#.........................
|
||||||
|
...#........................................................................................#...............................................
|
||||||
|
...........................................................................................................#......................#.........
|
||||||
|
..........#.......................................................................................#.........................................
|
||||||
|
......................#................#............................................#.................................................#.....
|
||||||
|
...........................#.....................#........#...................................................#.............................
|
|
@ -0,0 +1,184 @@
|
||||||
|
package day12
|
||||||
|
|
||||||
|
import (
|
||||||
|
"fmt"
|
||||||
|
"log"
|
||||||
|
"os"
|
||||||
|
"strconv"
|
||||||
|
"strings"
|
||||||
|
"sync"
|
||||||
|
"time"
|
||||||
|
)
|
||||||
|
|
||||||
|
func Run() int {
|
||||||
|
fmt.Println("hello day 12.")
|
||||||
|
|
||||||
|
start := time.Now()
|
||||||
|
|
||||||
|
filename := "day12/input"
|
||||||
|
bytes, err := os.ReadFile(filename)
|
||||||
|
if err != nil {
|
||||||
|
panic(fmt.Sprintf("error reading file %s\n", filename))
|
||||||
|
}
|
||||||
|
|
||||||
|
result := 0
|
||||||
|
text := string(bytes)
|
||||||
|
text = strings.TrimSpace(text)
|
||||||
|
|
||||||
|
// testMask, testBlocks := ReadLine(".??..??...?##. 1,1,3")
|
||||||
|
// blocksSum := 0
|
||||||
|
// for _, block := range testBlocks {
|
||||||
|
// blocksSum += block
|
||||||
|
// }
|
||||||
|
// testVariants := generatePermutations("", len(testMask), testBlocks, blocksSum, testMask)
|
||||||
|
// fmt.Printf("for mask %s and blocks %+v\n", testMask, testBlocks)
|
||||||
|
// for _, variant := range testVariants {
|
||||||
|
// fmt.Println(variant)
|
||||||
|
// }
|
||||||
|
|
||||||
|
var wg sync.WaitGroup
|
||||||
|
lines := strings.Split(text, "\n")
|
||||||
|
wg.Add(len(lines))
|
||||||
|
|
||||||
|
matches := make(chan int)
|
||||||
|
go func() {
|
||||||
|
wg.Wait()
|
||||||
|
close(matches)
|
||||||
|
}()
|
||||||
|
|
||||||
|
for i, line := range lines {
|
||||||
|
go func(line string, lineNum int){
|
||||||
|
mask, blockLengs := ReadLine(line)
|
||||||
|
|
||||||
|
blockLengthSum := 0
|
||||||
|
for _, blockLen := range blockLengs {
|
||||||
|
blockLengthSum += blockLen
|
||||||
|
}
|
||||||
|
|
||||||
|
memo := make(map[string]int)
|
||||||
|
variantsCount := generatePermutations("", len(mask), blockLengs, blockLengthSum, mask, memo)
|
||||||
|
|
||||||
|
log.Printf("%d : for line %s blocks %+v matches %d\n", lineNum, mask, blockLengs, variantsCount)
|
||||||
|
matches <- variantsCount
|
||||||
|
wg.Done()
|
||||||
|
}(line, i)
|
||||||
|
}
|
||||||
|
|
||||||
|
num := 0
|
||||||
|
for match := range matches {
|
||||||
|
num += 1
|
||||||
|
result += match
|
||||||
|
log.Printf("%d. intermediate: %d\n", num, result)
|
||||||
|
fmt.Printf("%d\n", result)
|
||||||
|
}
|
||||||
|
|
||||||
|
end := time.Now()
|
||||||
|
|
||||||
|
diff := end.Sub(start)
|
||||||
|
log.Printf("> calculated for %s", diff.String())
|
||||||
|
|
||||||
|
return result
|
||||||
|
}
|
||||||
|
|
||||||
|
func myRepeat(line, sep string, amount int) string {
|
||||||
|
acc := ""
|
||||||
|
for i := 0; i < amount; i++ {
|
||||||
|
acc += sep
|
||||||
|
acc += line
|
||||||
|
}
|
||||||
|
acc, _ = strings.CutPrefix(acc, sep)
|
||||||
|
|
||||||
|
return acc
|
||||||
|
}
|
||||||
|
|
||||||
|
// ???.### 1,1,3
|
||||||
|
func ReadLine(line string) (string, []int) {
|
||||||
|
firstSplit := strings.Split(line, " ")
|
||||||
|
if len(firstSplit) != 2 {
|
||||||
|
panic(fmt.Sprintf("error splitting %s into 2", line))
|
||||||
|
}
|
||||||
|
mask := firstSplit[0]
|
||||||
|
mask = myRepeat(mask, "?", 5)
|
||||||
|
blocks := firstSplit[1]
|
||||||
|
blocks = myRepeat(blocks, ",", 5)
|
||||||
|
// log.Printf(">> repeating blocks %s", blocks)
|
||||||
|
blockLengthStrings := strings.Split(blocks, ",")
|
||||||
|
blockLengs := make([]int, len(blockLengthStrings))
|
||||||
|
|
||||||
|
for i, blockLenStr := range blockLengthStrings {
|
||||||
|
num, err := strconv.Atoi(blockLenStr)
|
||||||
|
if err != nil {
|
||||||
|
panic(fmt.Sprintf("error extracting num %s from %s\n", blockLenStr, line))
|
||||||
|
}
|
||||||
|
blockLengs[i] = num
|
||||||
|
}
|
||||||
|
|
||||||
|
return mask, blockLengs
|
||||||
|
}
|
||||||
|
|
||||||
|
func generatePermutations(curString string, targetLength int, blockLengths []int, blockLengthsSum int, mask string, memo map[string]int) int {
|
||||||
|
|
||||||
|
memoKey := fmt.Sprintf("%+v|%d", blockLengths, len(curString))
|
||||||
|
memoized, memoFound := memo[memoKey]
|
||||||
|
if memoFound {
|
||||||
|
return memoized
|
||||||
|
}
|
||||||
|
|
||||||
|
// fmt.Printf("> entering with \n%s\nfor map \n%s\n\n", curString, mask)
|
||||||
|
// time.Sleep(time.Second)
|
||||||
|
if !isVariantMatchesMask(curString, mask) {
|
||||||
|
return 0
|
||||||
|
}
|
||||||
|
|
||||||
|
// log.Printf("> entering with %s\n", curString)
|
||||||
|
if len(blockLengths) == 0 {
|
||||||
|
if len(curString) > targetLength {
|
||||||
|
return 0
|
||||||
|
}
|
||||||
|
variant := curString + strings.Repeat(".", targetLength-len(curString))
|
||||||
|
if !isVariantMatchesMask(variant, mask) {
|
||||||
|
return 0
|
||||||
|
}
|
||||||
|
memo[memoKey] = 1
|
||||||
|
return 1
|
||||||
|
}
|
||||||
|
|
||||||
|
nextBlock := blockLengths[0]
|
||||||
|
restBlocks := blockLengths[1:]
|
||||||
|
|
||||||
|
if len(curString) + blockLengthsSum + len(blockLengths) - 1 > targetLength {
|
||||||
|
return 0
|
||||||
|
}
|
||||||
|
|
||||||
|
isLast := len(restBlocks) == 0
|
||||||
|
rightPointRepeat := 1
|
||||||
|
if isLast {
|
||||||
|
rightPointRepeat = 0
|
||||||
|
}
|
||||||
|
|
||||||
|
whenPass := curString + "."
|
||||||
|
whenAdd := curString + strings.Repeat("#", nextBlock) + strings.Repeat(".", rightPointRepeat)
|
||||||
|
|
||||||
|
passCount := generatePermutations(whenPass, targetLength, blockLengths, blockLengthsSum, mask, memo)
|
||||||
|
addCount := generatePermutations(whenAdd, targetLength, restBlocks, blockLengthsSum-nextBlock, mask, memo)
|
||||||
|
|
||||||
|
memo[memoKey] = passCount + addCount
|
||||||
|
return passCount + addCount
|
||||||
|
}
|
||||||
|
|
||||||
|
func isVariantMatchesMask(variant, mask string) bool {
|
||||||
|
if len(mask) < len(variant) {
|
||||||
|
log.Printf("mask %s is less than variant %s\n", mask, variant)
|
||||||
|
}
|
||||||
|
maskRunes := []rune(mask)
|
||||||
|
for i, symb := range variant {
|
||||||
|
if maskRunes[i] == '?' {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
if maskRunes[i] != symb {
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return true
|
||||||
|
}
|
|
@ -0,0 +1,6 @@
|
||||||
|
#.#.### 1,1,3
|
||||||
|
.#...#....###. 1,1,3
|
||||||
|
.#.###.#.###### 1,3,1,6
|
||||||
|
####.#...#... 4,1,1
|
||||||
|
#....######..#####. 1,6,5
|
||||||
|
.###.##....# 3,2,1
|
|
@ -0,0 +1,6 @@
|
||||||
|
???.### 1,1,3
|
||||||
|
.??..??...?##. 1,1,3
|
||||||
|
?#?#?#?#?#?#?#? 1,3,1,6
|
||||||
|
????.#...#... 4,1,1
|
||||||
|
????.######..#####. 1,6,5
|
||||||
|
?###???????? 3,2,1
|
File diff suppressed because it is too large
Load Diff
|
@ -0,0 +1,104 @@
|
||||||
|
#+title: Notes
|
||||||
|
* i guess let's generate all possible? and short circuit when they are not matching mask
|
||||||
|
how do i generate all possible?
|
||||||
|
|
||||||
|
i take length of the mask, that's max size
|
||||||
|
then for each step, either put . or put n # from the input.
|
||||||
|
|
||||||
|
add to current string, and do 2 recursive calls, one with diminished 'queue', one with same
|
||||||
|
* wrong answer on input
|
||||||
|
it's too high
|
||||||
|
|
||||||
|
and log shows:
|
||||||
|
|
||||||
|
2023/12/12 15:07:52 for line ???#?.?#?#.?#???#..? blocks [4 4 5 1] matches 2
|
||||||
|
|
||||||
|
and it should be 0
|
||||||
|
** huh, nope this looks good:
|
||||||
|
testMask := "???#?.?#?#.?#???#..?"
|
||||||
|
testBlocks := []int{4,4,5,1}
|
||||||
|
testVariants := generatePermutations("", len(testMask), testBlocks, 14, testMask)
|
||||||
|
fmt.Printf("for mask %s and blocks %+v\n", testMask, testBlocks)
|
||||||
|
fmt.Println(testVariants)
|
||||||
|
|
||||||
|
for mask ???#?.?#?#.?#???#..? and blocks [4 4 5 1]
|
||||||
|
[####..####..#####..# .####.####..#####..#]
|
||||||
|
** let's check this : for line ??????#???????? blocks [7 2] matches 21
|
||||||
|
** or this for line ?????.??#????? blocks [3 3 2 1] matches 3
|
||||||
|
looks ok
|
||||||
|
** this for line ??..??#?????#?##? blocks [1 1 1 1 4] matches 15
|
||||||
|
looks good
|
||||||
|
** for line ?#??#??#???.??.??.? blocks [1 2 3 1 1 1] matches 20
|
||||||
|
seems ok
|
||||||
|
** for line ???????#??.????####? blocks [1 1 1 1 1 6] matches 58
|
||||||
|
bingo?
|
||||||
|
|
||||||
|
for mask ???????#??.????####? and blocks [1 1 1 1 1 6]
|
||||||
|
#.#.#..#.#.######...
|
||||||
|
#.#.#..#.#..######..
|
||||||
|
#.#.#..#.#...######.
|
||||||
|
#.#.#..#.#....######
|
||||||
|
#.#.#..#...#.######.
|
||||||
|
#.#.#..#...#..######
|
||||||
|
#.#.#..#....#.######
|
||||||
|
#.#..#.#.#.######...
|
||||||
|
#.#..#.#.#..######..
|
||||||
|
#.#..#.#.#...######.
|
||||||
|
#.#..#.#.#....######
|
||||||
|
#.#..#.#...#.######.
|
||||||
|
#.#..#.#...#..######
|
||||||
|
#.#..#.#....#.######
|
||||||
|
#.#....#.#.#.######.
|
||||||
|
#.#....#.#.#..######
|
||||||
|
#.#....#.#..#.######
|
||||||
|
#..#.#.#.#.######...
|
||||||
|
#..#.#.#.#..######..
|
||||||
|
#..#.#.#.#...######.
|
||||||
|
#..#.#.#.#....######
|
||||||
|
#..#.#.#...#.######.
|
||||||
|
#..#.#.#...#..######
|
||||||
|
#..#.#.#....#.######
|
||||||
|
#..#...#.#.#.######.
|
||||||
|
#..#...#.#.#..######
|
||||||
|
#..#...#.#..#.######
|
||||||
|
#...#..#.#.#.######.
|
||||||
|
#...#..#.#.#..######
|
||||||
|
#...#..#.#..#.######
|
||||||
|
#....#.#.#.#.######.
|
||||||
|
#....#.#.#.#..######
|
||||||
|
#....#.#.#..#.######
|
||||||
|
.#.#.#.#.#.######...
|
||||||
|
.#.#.#.#.#..######..
|
||||||
|
.#.#.#.#.#...######.
|
||||||
|
.#.#.#.#.#....######
|
||||||
|
.#.#.#.#...#.######.
|
||||||
|
.#.#.#.#...#..######
|
||||||
|
.#.#.#.#....#.######
|
||||||
|
.#.#...#.#.#.######.
|
||||||
|
.#.#...#.#.#..######
|
||||||
|
.#.#...#.#..#.######
|
||||||
|
.#..#..#.#.#.######.
|
||||||
|
.#..#..#.#.#..######
|
||||||
|
.#..#..#.#..#.######
|
||||||
|
.#...#.#.#.#.######.
|
||||||
|
.#...#.#.#.#..######
|
||||||
|
.#...#.#.#..#.######
|
||||||
|
..#.#..#.#.#.######.
|
||||||
|
..#.#..#.#.#..######
|
||||||
|
..#.#..#.#..#.######
|
||||||
|
..#..#.#.#.#.######.
|
||||||
|
..#..#.#.#.#..######
|
||||||
|
..#..#.#.#..#.######
|
||||||
|
...#.#.#.#.#.######.
|
||||||
|
...#.#.#.#.#..######
|
||||||
|
...#.#.#.#..#.######
|
||||||
|
* well, maybe overnight will calculate.
|
||||||
|
but i guess i needed to check whether blocks are 'always' taking full width
|
||||||
|
then i'll only need to calculate once, and then multiply
|
||||||
|
** for example
|
||||||
|
2023/12/12 20:40:41 699 : for line ??#?????#???.? ???#?????#???.????#?????#???.????#?????#???.????#?????#???.? blocks [3 1 2 1 3 1 2 1 3 1 2 1 3 1 2 1 3 1 2 1] matches 38294856
|
||||||
|
|
||||||
|
??#?? ???#?? ?.?
|
||||||
|
3,1,2,1 - 10+3 = 13
|
||||||
|
|
||||||
|
lowest s ###.#.##.#..... - plenty of space for additional
|
|
@ -0,0 +1,226 @@
|
||||||
|
package day13
|
||||||
|
|
||||||
|
import (
|
||||||
|
"fmt"
|
||||||
|
"log"
|
||||||
|
"os"
|
||||||
|
"strings"
|
||||||
|
)
|
||||||
|
|
||||||
|
func Run() int {
|
||||||
|
filename := "day13/input"
|
||||||
|
fmt.Println("hello day 13.", filename)
|
||||||
|
bytes, err := os.ReadFile(filename)
|
||||||
|
if err != nil {
|
||||||
|
panic(fmt.Sprintf("error reading file %s", filename))
|
||||||
|
}
|
||||||
|
allText := string(bytes)
|
||||||
|
fieldTexts := strings.Split(allText, "\n\n")
|
||||||
|
|
||||||
|
result := 0
|
||||||
|
for _, fieldText := range fieldTexts {
|
||||||
|
field := ReadField(fieldText)
|
||||||
|
result += Calc(field)
|
||||||
|
}
|
||||||
|
|
||||||
|
return result
|
||||||
|
}
|
||||||
|
|
||||||
|
func Calc(field Field) int {
|
||||||
|
verticals, horizontals := field.initMirrors()
|
||||||
|
fmt.Println(field.String())
|
||||||
|
fmt.Printf("field width %d and height %d\n", len(field.Symbols[0]), len(field.Symbols))
|
||||||
|
|
||||||
|
for rowNum, row := range field.Symbols {
|
||||||
|
for colNum, symb := range row {
|
||||||
|
for _, horizontalMirrorUnderCheck := range horizontals {
|
||||||
|
// if horizontalMirrorUnderCheck.Smaller != 4 {
|
||||||
|
// continue
|
||||||
|
// }
|
||||||
|
mirroredRow, shouldCheck := horizontalMirrorUnderCheck.reflectCoord(rowNum)
|
||||||
|
// log.Println("for mirror", horizontalMirrorUnderCheck.String())
|
||||||
|
// log.Printf("> checking row %d and mirrored %d; should %t\n", rowNum, mirroredRow, shouldCheck)
|
||||||
|
if shouldCheck {
|
||||||
|
// log.Printf("checking horizontal mirror %+v", horizontalMirrorUnderCheck)
|
||||||
|
// log.Printf("in should check for row %d, col %d, mirrored row %d\n", rowNum, colNum, mirroredRow)
|
||||||
|
mirroredSymb := field.Symbols[mirroredRow][colNum]
|
||||||
|
isMirrored := symb == mirroredSymb
|
||||||
|
if !isMirrored {
|
||||||
|
// log.Printf("found not mirrored : %s != %s\n", string(symb), string(mirroredSymb))
|
||||||
|
horizontalMirrorUnderCheck.FailedLineChecks[rowNum] += 1
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// whole row got checked.
|
||||||
|
// let's mark successful line check for all that didn't fail this line check
|
||||||
|
for _, horizontalMirror := range horizontals {
|
||||||
|
_, failedCheckReported := horizontalMirror.FailedLineChecks[rowNum]
|
||||||
|
if !failedCheckReported {
|
||||||
|
horizontalMirror.SuccessfulLineChecks[rowNum] = struct{}{}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
rowsAboveHorizontals := 0
|
||||||
|
for _, mirr := range horizontals {
|
||||||
|
fmt.Println("horizontal: ", mirr.String())
|
||||||
|
if mirr.isFullMirror() {
|
||||||
|
log.Printf(">> found perfect Horizontal %+v\n", mirr)
|
||||||
|
rowsAboveHorizontals += (mirr.Smaller + 1)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
for colNum, _ := range field.Symbols[0] {
|
||||||
|
for rowNum, row := range field.Symbols {
|
||||||
|
symb := row[colNum]
|
||||||
|
for _, verticalMirrorUnderCheck := range verticals {
|
||||||
|
// if verticalMirrorUnderCheck.Smaller != 8 {
|
||||||
|
// continue
|
||||||
|
// }
|
||||||
|
mirroredCol, shouldCheck := verticalMirrorUnderCheck.reflectCoord(colNum)
|
||||||
|
if shouldCheck {
|
||||||
|
// log.Printf("checking vertical mirror %+v", verticalMirrorUnderCheck)
|
||||||
|
// log.Printf("in should check for row %d, col %d, mirrored col %d\n", rowNum, colNum, mirroredCol)
|
||||||
|
mirroredSymb := field.Symbols[rowNum][mirroredCol]
|
||||||
|
isMirrored := symb == mirroredSymb
|
||||||
|
if !isMirrored {
|
||||||
|
// log.Printf("found not mirrored : %s != %s\n", string(symb), string(mirroredSymb))
|
||||||
|
verticalMirrorUnderCheck.FailedLineChecks[colNum] += 1
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// whole row got checked.
|
||||||
|
// let's mark successful line check for all that didn't fail this line check
|
||||||
|
for _, verticalMirror := range verticals {
|
||||||
|
_, failedCheckReported := verticalMirror.FailedLineChecks[colNum]
|
||||||
|
if !failedCheckReported {
|
||||||
|
verticalMirror.SuccessfulLineChecks[colNum] = struct{}{}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
colsToLeftOfHorizontals := 0
|
||||||
|
for _, mirr := range verticals {
|
||||||
|
fmt.Println("vertical: ", mirr.String())
|
||||||
|
if mirr.isFullMirror() {
|
||||||
|
log.Printf(">> found perfect Vertical %+v\n", mirr)
|
||||||
|
colsToLeftOfHorizontals += (mirr.Smaller + 1)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
result := colsToLeftOfHorizontals + 100*rowsAboveHorizontals
|
||||||
|
|
||||||
|
return result
|
||||||
|
}
|
||||||
|
|
||||||
|
type Field struct {
|
||||||
|
Symbols [][]rune
|
||||||
|
}
|
||||||
|
|
||||||
|
func ReadField(fieldText string) Field {
|
||||||
|
fieldText = strings.TrimSpace(fieldText)
|
||||||
|
lines := strings.Split(fieldText, "\n")
|
||||||
|
|
||||||
|
symbols := make([][]rune, len(lines))
|
||||||
|
for i, line := range lines {
|
||||||
|
symbols[i] = []rune(line)
|
||||||
|
}
|
||||||
|
|
||||||
|
return Field{
|
||||||
|
Symbols: symbols,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func (f *Field) String() string {
|
||||||
|
text := "\n"
|
||||||
|
for _, row := range f.Symbols {
|
||||||
|
text += string(row)
|
||||||
|
text += "\n"
|
||||||
|
}
|
||||||
|
return text
|
||||||
|
}
|
||||||
|
|
||||||
|
func (f *Field) initMirrors() (vertical []Mirror, horizontal []Mirror) {
|
||||||
|
height := len(f.Symbols)
|
||||||
|
width := len(f.Symbols[0])
|
||||||
|
amountHorizontal := height - 1
|
||||||
|
amountVertical := width - 1
|
||||||
|
horizontal = make([]Mirror, amountHorizontal)
|
||||||
|
vertical = make([]Mirror, amountVertical)
|
||||||
|
|
||||||
|
for rowNum := 0; rowNum < amountHorizontal; rowNum++ {
|
||||||
|
maxDist := min(rowNum, height - 1 - (rowNum+1))
|
||||||
|
// log.Println("maxDist ", maxDist, "for rowNum ", rowNum)
|
||||||
|
horizontal[rowNum] = Mirror{
|
||||||
|
Smaller: rowNum,
|
||||||
|
Bigger: rowNum + 1,
|
||||||
|
SuccessfulLineChecks: make(map[int]any),
|
||||||
|
FailedLineChecks: make(map[int]int),
|
||||||
|
MaxDistToCheck: maxDist,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
for colNum := 0; colNum < amountVertical; colNum++ {
|
||||||
|
maxDist := min(colNum, width - 1 - (colNum+1))
|
||||||
|
vertical[colNum] = Mirror{
|
||||||
|
Smaller: colNum,
|
||||||
|
Bigger: colNum + 1,
|
||||||
|
SuccessfulLineChecks: make(map[int]any),
|
||||||
|
FailedLineChecks: make(map[int]int),
|
||||||
|
MaxDistToCheck: min(colNum, maxDist),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
type Mirror struct {
|
||||||
|
// located between lines
|
||||||
|
Smaller, Bigger int
|
||||||
|
MaxDistToCheck int // how many steps from mirrow have to be checked to confirm
|
||||||
|
// i.e if mirror between 0 and 1 - only rows 0 & 1 have to be checked, row 2 is 'mirrored' outside of the field and 'ok'
|
||||||
|
// value 0 means one step from 'mirror' so rows 0 and 1
|
||||||
|
SuccessfulLineChecks map[int]any
|
||||||
|
FailedLineChecks map[int]int // from line num, to amount of errors in that line
|
||||||
|
}
|
||||||
|
|
||||||
|
func (m *Mirror)isFullMirror() bool {
|
||||||
|
correctFailedLinesCount := len(m.FailedLineChecks) == 2
|
||||||
|
if correctFailedLinesCount {
|
||||||
|
for failedLine, failedSymbols := range m.FailedLineChecks {
|
||||||
|
reflectedLine, _ := m.reflectCoord(failedLine)
|
||||||
|
doublyReflected, _ := m.reflectCoord(reflectedLine)
|
||||||
|
// log.Printf(">>>> checking failed line %d, reflected is %d; doubly %d. amount failed is %d\n", failedLine, reflectedLine, doublyReflected, failedSymbols)
|
||||||
|
if failedSymbols == 1 && (doublyReflected == failedLine) {
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
|
||||||
|
func (m *Mirror)String() string {
|
||||||
|
return fmt.Sprintf("Mirror (full %t) between %d and %d. successful lines: %+v ; failed lines: %+v. Max check dist: %d\n",
|
||||||
|
m.isFullMirror(), m.Smaller, m.Bigger, m.SuccessfulLineChecks, m.FailedLineChecks, m.MaxDistToCheck)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (m *Mirror) reflectCoord(coord int) (reflected int, shouldCheck bool) {
|
||||||
|
dist := m.Smaller - coord
|
||||||
|
|
||||||
|
// _, distConfirmed := m.SuccessfulLineChecks[dist]
|
||||||
|
// if distConfirmed {
|
||||||
|
// // log.Printf("> getting dist confirmed for coord %d ; dist %d\n", coord, dist)
|
||||||
|
// return 0, false // either line already fully confirmed, or failed. no need for additional checks
|
||||||
|
// }
|
||||||
|
|
||||||
|
reflected = m.Bigger + dist
|
||||||
|
if dist < 0 {
|
||||||
|
dist = coord - m.Bigger
|
||||||
|
reflected = m.Smaller - dist
|
||||||
|
}
|
||||||
|
|
||||||
|
shouldCheck = dist <= m.MaxDistToCheck
|
||||||
|
|
||||||
|
return reflected, shouldCheck
|
||||||
|
}
|
|
@ -0,0 +1,15 @@
|
||||||
|
#.##..##.
|
||||||
|
..#.##.#.
|
||||||
|
##......#
|
||||||
|
##......#
|
||||||
|
..#.##.#.
|
||||||
|
..##..##.
|
||||||
|
#.#.##.#.
|
||||||
|
|
||||||
|
#...##..#
|
||||||
|
#....#..#
|
||||||
|
..##..###
|
||||||
|
#####.##.
|
||||||
|
#####.##.
|
||||||
|
..##..###
|
||||||
|
#....#..#
|
|
@ -0,0 +1,7 @@
|
||||||
|
#.##..##.
|
||||||
|
..#.##.#.
|
||||||
|
##......#
|
||||||
|
##......#
|
||||||
|
..#.##.#.
|
||||||
|
..##..##.
|
||||||
|
#.#.##.#.
|
|
@ -0,0 +1,7 @@
|
||||||
|
#...##..#
|
||||||
|
#....#..#
|
||||||
|
..##..###
|
||||||
|
#####.##.
|
||||||
|
#####.##.
|
||||||
|
..##..###
|
||||||
|
#....#..#
|
File diff suppressed because it is too large
Load Diff
6
main.go
6
main.go
|
@ -3,12 +3,12 @@ package main
|
||||||
import (
|
import (
|
||||||
"log"
|
"log"
|
||||||
|
|
||||||
"sunshine.industries/aoc2023/day10"
|
"sunshine.industries/aoc2023/day13"
|
||||||
)
|
)
|
||||||
|
|
||||||
func main() {
|
func main() {
|
||||||
log.Print("> starting run:")
|
log.Print("> starting run:")
|
||||||
|
|
||||||
result := day10.Run()
|
result := day13.Run()
|
||||||
log.Printf("day10 result: %d\n****\n", result)
|
log.Printf("day13 result: %d\n****\n", result)
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue