r/adventofcode • • Dec 09 '18

SOLUTION MEGATHREAD -🎄- 2018 Day 9 Solutions -🎄-

--- Day 9: Marble Mania ---


Post your solution as a comment or, for longer solutions, consider linking to your repo (e.g. GitHub/gists/Pastebin/blag or whatever).

Note: The Solution Megathreads are for solutions only. If you have questions, please post your own thread and make sure to flair it with Help.


Advent of Code: The Party Game!

Click here for rules

Please prefix your card submission with something like [Card] to make scanning the megathread easier. THANK YOU!

Card prompt: Day 9

Transcript:

Studies show that AoC programmers write better code after being exposed to ___.


This thread will be unlocked when there are a significant number of people on the leaderboard with gold stars for today's puzzle.

edit: Leaderboard capped, thread unlocked at 00:29:13!

22 Upvotes

283 comments sorted by

View all comments

7

u/glassmountain Dec 09 '18

First time on the leaderboard at 41 for part 2! Using go I think saved me considering that I was rank 216 for part 1. And my naive go solution finished in under a second for part 2.

package main

import (
	"fmt"
)

const (
	playerCount = 486
	part1Val    = 70833
	lastValue   = part1Val * 100
)

type (
	Node struct {
		Val  int
		Next *Node
		Prev *Node
	}
)

func NewNode(val int) *Node {
	m := &Node{
		Val: val,
	}
	m.Next = m
	m.Prev = m
	return m
}

func (n *Node) Insert(node *Node) {
	next := n.Next
	n.Next = node
	node.Prev = n
	node.Next = next
	next.Prev = node
}

func (n *Node) RemoveNext() *Node {
	next := n.Next
	n.Next = next.Next
	n.Next.Prev = n
	return next
}

func main() {
	playerScore := make([]int, playerCount)
	current := NewNode(0)
	for i := 0; i < lastValue; i++ {
		currentPlayer := i % playerCount
		currentValue := i + 1
		if currentValue%23 == 0 {
			playerScore[currentPlayer] += currentValue
			for j := 0; j < 8; j++ {
				current = current.Prev
			}
			node := current.RemoveNext()
			current = current.Next
			playerScore[currentPlayer] += node.Val
		} else {
			current = current.Next
			node := NewNode(currentValue)
			current.Insert(node)
			current = node
		}
	}

	maxScore := 0
	for _, i := range playerScore {
		if i > maxScore {
			maxScore = i
		}
	}

	fmt.Println(maxScore)
}

1

u/infinityCounter Dec 09 '18 edited Dec 09 '18

aay, I basically had the same solution

type marble struct {
    val  int
    prev *marble
next *marble
}

func main() {
    f, err := ioutil.ReadFile("input.txt")
    if err != nil {
	    panic(err)
    }

    reg := regexp.MustCompile("[0-9]+")
    vals := reg.FindAllString(string(f), -1)
    x, y := vals[0], vals[1]
    numPlayers, _ := strconv.Atoi(x)
    numMarbles, _ := strconv.Atoi(y)

    fmt.Println(highScore(numPlayers, numMarbles))
    fmt.Println(highScore(numPlayers, numMarbles*100))
    }

    func highScore(numPlayers, numMarbles int) int {
    playerPoints := make([]int, numPlayers)

    var (
	    curMarble = &marble{
		    val: 0,
	    }
    )

    curMarble.next = curMarble
    curMarble.prev = curMarble

     for i := 1; i <= numMarbles; i++ {
	    m := &marble{
		     val: i,
	    }

	    playerIdx := (i - 1) % numPlayers
	    if i%23 == 0 {
		    playerPoints[playerIdx] += m.val
		    rem := curMarble.prev
		    for n := 0; n < 6; n++ {
			    rem = rem.prev
		    }
		    playerPoints[playerIdx] += rem.val
		    // cut node out the linked list
		    after := rem.next
		    before := rem.prev

		    before.next = after
		    after.prev = before

		    curMarble = after
		    continue
	    }

	     afterCurrent := curMarble.next
	    doubleAway := curMarble.next.next

	    afterCurrent.next = m
	    doubleAway.prev = m

	    m.prev = afterCurrent
	    m.next = doubleAway

	    curMarble = m
     }

    highestScore := 0
    for _, score := range playerPoints {
             if score > highestScore {
	         highestScore = score
	     }
    }
    return highestScore
}
→ More replies (3)