adventofcode

Chase 2023-12-02T01:46:31.366409Z

One of my usual AOC habits is to explore transducers after I get my quick and dirty answer out there. I'm curious why my regular version is the same speed (if not slightly faster) when benchmarking with criterium than the transducer version. I usually find quite the opposite.

Chase 2023-12-02T01:46:41.001549Z

relevant code for Part 1:

(defn part-1 [data]
  (->> data
       (map #(re-seq #"\d" %))
       (map (juxt first last))
       (map (comp parse-long (partial apply str)))
       (reduce +)))

(defn part-1-transduce [data]
  (let [xform (comp
                (map #(re-seq #"\d" %))
                (map (juxt first last))
                (map (comp parse-long (partial apply str))))]
    (transduce xform + data)))

borkdude 2023-12-02T13:19:46.348499Z

It probably depends on the size of the data

AC 2023-12-02T05:36:40.495109Z

solving day 2 just reminds me how much I love programming in clojure.

2023-12-02T05:40:00.888119Z

Day 02 - Solutions

V 2023-12-10T21:45:54.131899Z

(ns day02
  (:require [ :as io]
            [clojure.string :as string]))

(defn parse-subset [subset]
  (let [[[_ r]] (re-seq #"(\d+) red" subset)
        [[_ g]] (re-seq #"(\d+) green" subset)
        [[_ b]] (re-seq #"(\d+) blue" subset)]
    [(or (some-> r parse-long) 0)
     (or (some-> g parse-long) 0)
     (or (some-> b parse-long) 0)]))

(defn parse [line]
  (let [[_ subsets] (string/split line #":")]
    (->>  (string/split subsets #";")
          (map parse-subset))))

(defn part01 [lines]
  (->> lines
       (map parse)
       (map-indexed
        (fn [idx subsets]
          [(+ idx 1)
           (->> subsets
                (map (fn [[r g b]] (and (<= r 12) (<= g 13) (<= b 14))))
                (flatten)
                (every? identity))]))
       (filter (fn [[_ p]] p))
       (map first)
       (reduce +)))

(defn part02 [lines]
  (->> lines
       (map parse)
       (map
        (fn [subsets]
          (->> subsets
               (reduce (fn [[ar ag ab] [r g b]]
                         [(max ar r) (max ag g) (max ab b)])
                       [0 0 0])
               (reduce *))))
       (reduce +)))

(comment
  (with-open [r (io/reader "day02.txt")]
    (part01 (line-seq r)))
  (with-open [r (io/reader "day02.txt")]
    (part02 (line-seq r))))

R.A. Porter 2023-12-02T06:01:52.452169Z

Mine's a little clunky, but gets the job done. https://coyotesqrl.github.io/advent-of-code/2023/src/coyotesqrl/2023/day02/

wevrem 2023-12-02T06:06:47.668069Z

Happily, my approach for part 1 dovetailed nicely with part 2, didn’t have to re-write anything, and that rarely happens for me with AoC.

fingertoe 2023-12-02T07:15:18.411279Z

https://gist.github.com/jreighley/14ec18793fe5bb9bbdee41493dbe2edd merge-with max came in quite handy.

🀯 2
Sam Ferrell 2023-12-02T07:16:24.164499Z

> merge-with max came in quite handy. this is great, did not know about this! +1

Casey 2023-12-02T07:33:13.192179Z

yea, same, i happened to set myself up very nicely for part 2 during part 1. https://github.com/Ramblurr/advent-of-code/blob/main/src/aoc/2023/day02.clj

Ryan Martin 2023-12-02T07:33:35.183909Z

probably influenced by day 1, but I keep coming back to regex for my solutions: https://github.com/rmrt1n/advent-of-code-2023-clj/blob/main/src/aoc/day02.clj

karlis 2023-12-02T07:59:44.351879Z

Had to rewrite parsing logic when part 2 was unveiled, but overall happy how easy today turned out to be https://github.com/skazhy/advent/blob/master/src/advent/2023/day2.clj

2023-12-04T10:09:06.798259Z

https://squint-cljs.github.io/squint/?boilerplate=https%3A%2F%2Fgist.githubusercontent.com%2Fborkdude%2Fcf94b492d948f7f418aa81ba54f428ff%2Fraw%2F3e871513ab6f2462841f75fc99668f841f33dabb%2Faoc_ui.cljs&amp;repl=true&amp;src=OzsgSGVscGVyIGZ1bmN0aW9uczoKOzsgKGZldGNoLWlucHV0IHllYXIgZGF5KSAtIGdldCBBT0MgaW5wdXQKOzsgKGFwcGVuZCBzdHIpIC0gYXBwZW5kIHN0ciB0byBET00KOzsgKHNweSB4KSAtIGxvZyB4IHRvIGNvbnNvbGUgYW5kIHJldHVybiB4CgooZGVmIGlucHV0ICgtPj4gKGpzLWF3YWl0IChmZXRjaC1pbnB1dCAyMDIzIDIpKQogICAgICAgICAgICAgc3RyL3NwbGl0LWxpbmVzKSkKCihkZWYgYmFnCiAgeyJyZWQiIDEyCiAgICJncmVlbiIgMTMKICAgImJsdWUiIDE0fSkKCihkZWZuIHNwbGl0LWN1YmVzCiAgW2N1YmVzXQogICgtPj4gKHN0ci9zcGxpdCBjdWJlcyAiLCAiKQogICAgKG1hcHYgIyhsZXQgW1tuIGNvbG9yXSAoc3RyL3NwbGl0ICUgIiAiKV0KICAgICAgICAgICAgIHtjb2xvciBufSkpCiAgICAoaW50byB7fSkpKQoKKGRlZm4gY29sb3ItcG9zc2libGU%2FCiAgW1tjb2xvciBuXV0KICAoPj0gKGdldCBiYWcgY29sb3IpIG4pKQoKKGRlZm4gcG9zc2libGU%2FCiAgW3NldF0KICAoZXZlcnk%2FIGNvbG9yLXBvc3NpYmxlPyBzZXQpKQoKKGRlZm4gcGFyc2UtZ2FtZQogIFtzXQogIChsZXQgW1tnYW1lIHNldHNdIChzdHIvc3BsaXQgcyAiOiAiKQogICAgICAgIHBhcnNlZC1zZXRzICgtPj4gKHN0ci9zcGxpdCBzZXRzICI7ICIpCiAgICAgICAgICAgICAgICAgICAgICAobWFwdiBzcGxpdC1jdWJlcykpCiAgICAgICAgcG9zc2libGUtYmFnIChhcHBseSBtZXJnZS13aXRoIG1heCBwYXJzZWQtc2V0cyldCiAgICB7OmdhbWUgKC0%2BIChzdHIvc3BsaXQgZ2FtZSAiICIpIGxhc3QgcGFyc2UtbG9uZykKICAgICA6c2V0cyBwYXJzZWQtc2V0cwogICAgIDpwb3NzaWJsZS1iYWcgcG9zc2libGUtYmFnCiAgICAgOnBvd2VyLXNldCAoLT4%2BIHBvc3NpYmxlLWJhZwogICAgICAgICAgICAgICAgICB2YWxzCiAgICAgICAgICAgICAgICAgIHNweQogICAgICAgICAgICAgICAgICAoYXBwbHkgKikpCiAgICAgOnBvc3NpYmxlPyAoZXZlcnk%2FIHBvc3NpYmxlPyBwYXJzZWQtc2V0cyl9KSkKCihkZWYgcGFyc2VkLWdhbWUgKG1hcHYgcGFyc2UtZ2FtZSBpbnB1dCkpCgooLT4%2BIHBhcnNlZC1nYW1lCiAgICAoZmlsdGVyIDpwb3NzaWJsZT8pCiAgICAobWFwIDpnYW1lKQogICAgKGFwcGx5ICspCiAgYXBwZW5kKQoKKC0%2BPiBwYXJzZWQtZ2FtZQogIChtYXB2IDpwb3dlci1zZXQpCiAgKGFwcGx5ICspCiAgYXBwZW5kKQ%3D%3D using the squint playground. merge-with max feels like cheating on part 2.

borkdude 2023-12-04T10:10:54.829979Z

πŸ‘

borkdude 2023-12-04T10:11:27.196019Z

@mynomoto I wonder if you will manage day 3 with squint, as storing collections as keys doesn't work that well in JS. You can switch to http://squint-cljs.github.io/cherry if you must :)

borkdude 2023-12-04T10:11:42.258979Z

(but I'd like to challenge you to do it in squint anyway :))

1
2023-12-04T10:14:38.368339Z

I will at least try, let's see how it goes πŸ˜‰

borkdude 2023-12-04T10:17:20.742759Z

one strategy I've used is to use an object instead of a set and store coordinates like:

(assoc {} coord coord)
This will become {"0,0" [0,0]} in JS

borkdude 2023-12-04T10:17:31.305069Z

and then also (get obj [0,0]) works

borkdude 2023-12-04T10:17:44.830579Z

it works only for 1-dimensional arrays though

mrnhrd 2023-12-04T18:51:11.470909Z

this was comparatively easier than day 1. Though tons of str/split feels like a code smell: https://gist.github.com/mrnhrd/895b6ad912e3b04d941ab3a943b42678 looking forward to scrolling through other people's solutions.

pez 2023-12-03T13:28:30.327569Z

Decided to go for TDD, because parsing input always gets trickier than I think it will. πŸ˜ƒ

maleghast 2023-12-03T17:40:54.060149Z

Would love to know from others better at data parsing and shaping how I could have done the data parsing and shaping more efficiently, but for the sake of posterity… https://gist.github.com/maleghast/22d460542ce8f313fb6db54cd92f2196

pez 2023-12-03T20:03:52.047589Z

@maleghast I too felt like I had made the parsing a bit harder than it really is. When I had collected the stars, I asked ChatGPT to write a parser and it did a pretty decent job, I’d say: https://chat.openai.com/share/33e05353-b5e6-45d9-851f-1b532daf0ebb

Cora (she/her) 2023-12-03T20:04:55.148879Z

the format is really easy to just use splits for, thankfully

pez 2023-12-03T20:05:33.341609Z

Yeah, that’s what ChatGPT realized, but I only realized halfly. πŸ˜ƒ

Jan Tore Stolsvik 2023-12-02T09:19:29.843329Z

Happy with how easy part two was to adapt to :) https://github.com/jantorestolsvik/advent-of-code-2023/blob/main/src/day02.clj

2023-12-02T09:45:34.484799Z

Somehow sorted-map becomes the main data structure so far... https://github.com/caseneuve/aoc2023/blob/master/day02/solution.clj

πŸ†’ 1
borkdude 2023-12-02T11:20:15.693159Z

Bangs head on keyboard, after a non-optimal night of sleep. The test input works for me, but the "production" input gives a too low number

borkdude 2023-12-02T11:29:30.214149Z

https://squint-cljs.github.io/squint/?boilerplate=https%3A%2F%2Fgist.githubusercontent.com%2Fborkdude%2Fcf94b492d948f7f418aa81ba54f428ff%2Fraw%2Fa7da6236e9670681a93761b81fd66ad26c119164%2Faoc_ui.cljs&amp;repl=true&amp;src=OzsgSGVscGVyIGZ1bmN0aW9uczoKOzsgKGZldGNoLWlucHV0IHllYXIgZGF5KSAtIGdldCBBT0MgaW5wdXQKOzsgKGFwcGVuZCBzdHIpIC0gYXBwZW5kIHN0ciB0byBET00KOzsgKHNweSB4KSAtIGxvZyB4IHRvIGNvbnNvbGUgYW5kIHJldHVybiB4CgooZGVmbiBwYXJzZS1saW5lIFtsaW5lXQogIChsZXQgW1tpZCBnYW1lXSAoc3RyL3NwbGl0IGxpbmUgIjogIikKICAgICAgICBpZCAoLT4gKHN0ci9yZXBsYWNlIGlkICJHYW1lICIgIiIpCiAgICAgICAgICAgICBwYXJzZS1sb25nKV0KICAgIHs6aWQgaWQKICAgICA6Z2FtZSAoLT4KICAgICAgICAgICAgIGdhbWUKICAgICAgICAgICAgIChzdHIvc3BsaXQgIjsgIikKICAgICAgICAgICAgICgtPj4gKG1hcCAoZm4gW2VdCiAgICAgICAgICAgICAgICAgICAgICAgICAoLT4gKG1hcHYKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICMoLT4gKHJldmVyc2UgKHN0ci9zcGxpdCAlICIgIikpCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICh1cGRhdGUgMSBwYXJzZS1sb25nKSkKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIChzdHIvc3BsaXQgZSAiLCAiKSkpKSkKICAgICAgICAgICAgICAgKG1hcHYgIyhpbnRvIHt9ICUpKSkpfSkpCgooY29tbWVudAogIChwYXJzZS1saW5lICJHYW1lIDE6IDMgYmx1ZSwgNCByZWQ7IDIgZ3JlZW4iKQogICkKCihkZWYgZXhhbXBsZSAiR2FtZSAxOiAzIGJsdWUsIDQgcmVkOyAxIHJlZCwgMiBncmVlbiwgNiBibHVlOyAyIGdyZWVuCkdhbWUgMjogMSBibHVlLCAyIGdyZWVuOyAzIGdyZWVuLCA0IGJsdWUsIDEgcmVkOyAxIGdyZWVuLCAxIGJsdWUKR2FtZSAzOiA4IGdyZWVuLCA2IGJsdWUsIDIwIHJlZDsgNSBibHVlLCA0IHJlZCwgMTMgZ3JlZW47IDUgZ3JlZW4sIDEgcmVkCkdhbWUgNDogMSBncmVlbiwgMyByZWQsIDYgYmx1ZTsgMyBncmVlbiwgNiByZWQ7IDMgZ3JlZW4sIDE1IGJsdWUsIDE0IHJlZApHYW1lIDU6IDYgcmVkLCAxIGJsdWUsIDMgZ3JlZW47IDIgYmx1ZSwgMSByZWQsIDIgZ3JlZW4iKQoKKGRlZiBpbnB1dCAoLT4%2BIChqcy1hd2FpdCAoZmV0Y2gtaW5wdXQgMjAyMyAyKSkKICAgICAgICAgICAgICNfc3B5CiAgICAgICAgICAgICBzdHIvdHJpbQogICAgICAgICAgICAgc3RyL3NwbGl0LWxpbmVzCiAgICAgICAgICAgICAobWFwdiBwYXJzZS1saW5lKSkpCgooY29tbWVudAogIChzcHkgaW5wdXQpKQoKKGRlZm4gbXktcGx1cyBbJiB4c10KICAoYXBwbHkgKyAobWFwIChmbmlsIGlkZW50aXR5IDApIHhzKSkpCgooY29tbWVudAogIChteS1wbHVzIDEganMvdW5kZWZpbmVkIDIganMvdW5kZWZpbmVkKSkKCihkZWZuIHN1bS1nYW1lIFtnYW1lXQogIChhcHBseSBtYXB2IG15LXBsdXMKICAgIChtYXB2IChqdXh0IDpyZWQgOmdyZWVuIDpibHVlKSBnYW1lKSkpCgooY29tbWVudAogIChzdW0tZ2FtZSBbezpyZWQgMSA6Ymx1ZSAyIDpncmVlbiAzfQogICAgICAgICAgICAgezpyZWQgNSA6Ymx1ZSAxMzM3fV0pKQoKKGRlZm4gcGFydC0xCiAgW10KICAoLT4%2BIGlucHV0CiAgICAoZmlsdGVydiAjKGxldCBbZ2FtZSAoOmdhbWUgJSkKICAgICAgICAgICAgICAgICAgICBbciBnIGJdIChzdW0tZ2FtZSBnYW1lKV0KICAgICAgICAgICAgICAgIChhbmQKICAgICAgICAgICAgICAgICAgKDw9IHIgMTIpCiAgICAgICAgICAgICAgICAgICg8PSBnIDEzKQogICAgICAgICAgICAgICAgICAoPD0gYiAxNCkpKSkKICAgIChtYXB2IDppZCkKICAgIChhcHBseSArKSkpCgooY29tbWVudAogIChwYXJ0LTEpKQ%3D%3D - any hints welcome, I'm going off for lunch ;)

😍 2
borkdude 2023-12-02T11:33:11.542989Z

I think I got it, I misinterpreted the puzzle, I summed all the red, green, blue and then compared to the max

borkdude 2023-12-02T11:35:57.161589Z

That's it, part 1 fixed

Ryan Martin 2023-12-02T11:37:02.839939Z

I had the same mistake, summed the colors instead of using max

borkdude 2023-12-02T11:37:23.793939Z

facepalm

oyakushev 2023-12-02T11:46:06.020139Z

@michaeljweaver Love how terse your implementation is! The parsing part certainly took me a while to understand. Also, power could just be #(apply * (vals %)) . Ah, I see that it couldn't, since you keep game id as one of the keys.

borkdude 2023-12-02T11:53:14.049339Z

I thought I made a mistake earlier by using array indexes as the game id but then I thought: perhaps they use sparse ids, but this wasn't the case in my input

tschady 2023-12-02T12:28:23.339039Z

β€’ Sometimes I find spelling out the parser easier to read, though I’m not completely happy with mine it was fast. β€’ using [r g b] tuples in a matrix lets you do things like map >= to check size and makes power just the max of the transpose. https://github.com/tschady/advent-of-code/blob/main/src/aoc/2023/d02.clj

borkdude 2023-12-02T12:28:39.857619Z

https://squint-cljs.github.io/squint/?boilerplate=https%3A%2F%2Fgist.githubusercontent.com%2Fborkdude%2Fcf94b492d948f7f418aa81ba54f428ff%2Fraw%2Fa7da6236e9670681a93761b81fd66ad26c119164%2Faoc_ui.cljs&repl=true&src=OzsgSGVscGVyIGZ1bmN0aW9uczoKOzsgKGZldGNoLWlucHV0IHllYXIgZGF5KSAtIGdldCBBT0MgaW5wdXQKOzsgKGFwcGVuZCBzdHIpIC0gYXBwZW5kIHN0ciB0byBET00KOzsgKHNweSB4KSAtIGxvZyB4IHRvIGNvbnNvbGUgYW5kIHJldHVybiB4CgooZGVmIGlucHV0ICgtPiAoanMtYXdhaXQgKGZldGNoLWlucHV0IDIwMjMgMikpCiAgICAgICAgICAgICBzdHIvdHJpbQogICAgICAgICAgICAgc3RyL3NwbGl0LWxpbmVzKSkKCihkZWZuIGdhbWVzIFtzXQogICgtPj4gKC0%2BIHMgKHN0ci9zcGxpdCAjIjoiKSBzZWNvbmQKICAgICAgICAgKHN0ci9yZXBsYWNlICMiKFxkKykgKFx3KykiICJ7XCIkMlwiOiAkMX0iKQogICAgICAgICAoc3RyL3NwbGl0ICMiWyw7XSIpKQogICAgKG1hcCBqcy9KU09OLnBhcnNlKQogICAgKGFwcGx5IG1lcmdlLXdpdGggbWF4KQogICAgKChqdXh0IDpyZWQgOmdyZWVuIDpibHVlKSkpKQoKKGNvbW1lbnQKICAoZ2FtZXMgKGZpcnN0IGlucHV0KSkpCgooZGVmIHAxCiAgKGxldCBbcnVsZXMgKHZhbHMgeyJyZWQiIDEyICJncmVlbiIgMTMgImJsdWUiIDE0fSkKICAgICAgICBwb3NzaWJsZT8gIyhldmVyeT8gdHJ1ZT8gKG1hcCAoZm4gW2EgYl0KICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICg8PSBhIGIpKSAlIHJ1bGVzKSldCiAgICAocGFydGlhbCBrZWVwLWluZGV4ZWQKICAgICAgKGZuIFtpZCBnYW1lXSAod2hlbiAocG9zc2libGU%2FIGdhbWUpIChpbmMgaWQpKSkpKSkKCihkZWYgcDIgKHBhcnRpYWwgbWFwICMocmVkdWNlIChmbiBbYSBiXSAoKiBhIGIpKSAlKSkpCgooZGVmbiBzb2x2ZSBbaW5wdXRdCiAgKGxldCBbc29sdmUtd2l0aCAjKC0%2BPiBpbnB1dCAobWFwIGdhbWVzKSAlIChhcHBseSArKSldCiAgICB7OnBhcnQxIChzb2x2ZS13aXRoIHAxKSA6cGFydDIgKHNvbHZlLXdpdGggcDIpfSkpCgooY29tbWVudAogIChzb2x2ZSBpbnB1dCkpCgooY29tbWVudAogIChkZWYgdGVzdC1pbnB1dCAiR2FtZSAxOiAzIGJsdWUsIDQgcmVkOyAxIHJlZCwgMiBncmVlbiwgNiBibHVlOyAyIGdyZWVuCkdhbWUgMjogMSBibHVlLCAyIGdyZWVuOyAzIGdyZWVuLCA0IGJsdWUsIDEgcmVkOyAxIGdyZWVuLCAxIGJsdWUKR2FtZSAzOiA4IGdyZWVuLCA2IGJsdWUsIDIwIHJlZDsgNSBibHVlLCA0IHJlZCwgMTMgZ3JlZW47IDUgZ3JlZW4sIDEgcmVkCkdhbWUgNDogMSBncmVlbiwgMyByZWQsIDYgYmx1ZTsgMyBncmVlbiwgNiByZWQ7IDMgZ3JlZW4sIDE1IGJsdWUsIDE0IHJlZApHYW1lIDU6IDYgcmVkLCAxIGJsdWUsIDMgZ3JlZW47IDIgYmx1ZSwgMSByZWQsIDIgZ3JlZW4iKQogIChkZWYgc29sdmUtd2l0aCAjKC0%2BPiB0ZXN0LWlucHV0CiAgICAgICAgICAgICAgICAgICAgIHN0ci9zcGxpdC1saW5lcwogICAgICAgICAgICAgICAgICAgICAobWFwIGdhbWVzKSAlCiAgICAgICAgICAgICAgICAgICAgIChhcHBseSArKSkpCiAgCiAgKD0gOCAoc29sdmUtd2l0aCBwMSkpCiAgKD0gMjI4NiAoc29sdmUtd2l0aCBwMikpCiAgKQ%3D%3D The above is @piotr.kaznowski’s solution. I used JSON/parse instead of read-string and there were some issues around * and <= not being available as reified functions (https://github.com/squint-cljs/squint/issues/400)

πŸ™Œ 1
2023-12-02T13:25:27.958769Z

(require '[clojure.string :as str])

(defn parse-count [s]
  (let [[cnt color] (str/split s #" ")]
    [(keyword color) (parse-long cnt)]))

(defn parse-hand [s]
  (->> (str/split s #", ")
       (map parse-count)
       (into {})))

(defn game-maxes [s]
  (let [[game-name-str counts-str] (str/split s #": ")
        max-counts (-> counts-str
                       (str/split #"; ")
                       (->> (map parse-hand)
                            (apply merge-with max)))
        game-id (-> game-name-str (str/split #" ")
                    second
                    parse-long)]
    [game-id max-counts]))

(def thresholds {:red 12 :green 13 :blue 14})

(defn game-within-threshold? [[_game-id maxes]]
  (->> (merge-with >= thresholds maxes)
       vals
       (every? true?)))

(defn power-val [[_game-id maxes]]
  (->> maxes
       vals
       (reduce *)))

(def part1-result
  (-> (slurp "aoc/input2.txt")
      (str/split #"\n")
      (->> (map game-maxes)
           (filter game-within-threshold?)
           (map first)
           (reduce +))))

(def part2-result
  (-> (slurp "aoc/input2.txt")
      (str/split #"\n")
      (->> (map game-maxes)
           (map power-val)
           (reduce +))))

carnundotcom 2023-12-02T13:32:24.909769Z

less to get snagged on than with Day 1 πŸ™‚

(defn possible? [game]
  (let [c->max {"red" 12, "green" 13, "blue" 14}]
    ;; for every selection in this game...
    (every? #(every? (fn [c] ; ... every color <= max (or absent)
                       (<= (get % c 0) (get c->max c)))
                     (keys c->max))
            (:cubes game))))


;; part 2
(defn min-cubes [game]
  ;; reduce over all 'cubes' (selections of cubes) in this game...
  (reduce (fn [m cube]
            (->> m
                 ;; ... to produce a map of min required for each color
                 (map (fn [[c n]] [c (max n (get cube c 0))]))
                 (into {})))
          {"red" 0
           "green" 0
           "blue" 0}
          (:cubes game)))


(defn solve [input & {:keys [part]}]
  (->> (parse input)
       (keep (fn [game]
               (case part
                 1 (when (possible? game)
                     (:id game))
                 2 (->> (min-cubes game)
                        (vals)
                        (apply *)))))
       (apply +)))
https://github.com/CarnunMP/Advent-of-Code/blob/master/src/y2023/d2.clj (if this trend continues...??)

borkdude 2023-12-02T13:42:07.678569Z

@larzeitlin https://squint-cljs.github.io/squint/?boilerplate=https%3A%2F%2Fgist.githubusercontent.com%2Fborkdude%2Fcf94b492d948f7f418aa81ba54f428ff%2Fraw%2Fa7da6236e9670681a93761b81fd66ad26c119164%2Faoc_ui.cljs&amp;repl=true&amp;src=OzsgSGVscGVyIGZ1bmN0aW9uczoKOzsgKGZldGNoLWlucHV0IHllYXIgZGF5KSAtIGdldCBBT0MgaW5wdXQKOzsgKGFwcGVuZCBzdHIpIC0gYXBwZW5kIHN0ciB0byBET00KOzsgKHNweSB4KSAtIGxvZyB4IHRvIGNvbnNvbGUgYW5kIHJldHVybiB4CgoocmVxdWlyZSAnW2Nsb2p1cmUuc3RyaW5nIDphcyBzdHJdKQoKKGRlZm4gcGFyc2UtY291bnQgW3NdCiAgKGxldCBbW2NudCBjb2xvcl0gKHN0ci9zcGxpdCBzICMiICIpXQogICAgWygjPyg6c3F1aW50IGlkZW50aXR5IDpkZWZhdWx0IGtleXdvcmQpIGNvbG9yKSAocGFyc2UtbG9uZyBjbnQpXSkpCgooY29tbWVudAogIChwYXJzZS1jb3VudCAiMSBncmVlbiIpKQoKKGRlZm4gcGFyc2UtaGFuZCBbc10KICAoLT4%2BIChzdHIvc3BsaXQgcyAjIiwgIikKICAgIChtYXAgcGFyc2UtY291bnQpCiAgICAoaW50byB7fSkpKQoKKGNvbW1lbnQKICAocGFyc2UtaGFuZCAiMSBncmVlbiwgMiBibHVlIikpCgooZGVmbiBnYW1lLW1heGVzIFtzXQogIChsZXQgW1tnYW1lLW5hbWUtc3RyIGNvdW50cy1zdHJdIChzdHIvc3BsaXQgcyAjIjogIikKICAgICAgICBtYXgtY291bnRzICgtPiBjb3VudHMtc3RyCiAgICAgICAgICAgICAgICAgICAgIChzdHIvc3BsaXQgIyI7ICIpCiAgICAgICAgICAgICAgICAgICAgICgtPj4gKG1hcCBwYXJzZS1oYW5kKQogICAgICAgICAgICAgICAgICAgICAgIChhcHBseSBtZXJnZS13aXRoIG1heCkpKQogICAgICAgIGdhbWUtaWQgKC0%2BIGdhbWUtbmFtZS1zdHIgKHN0ci9zcGxpdCAjIiAiKQogICAgICAgICAgICAgICAgICBzZWNvbmQKICAgICAgICAgICAgICAgICAgcGFyc2UtbG9uZyldCiAgICBbZ2FtZS1pZCBtYXgtY291bnRzXSkpCgooY29tbWVudAogIChnYW1lLW1heGVzICJHYW1lIDE6IDEgZ3JlZW4sIDIgYmx1ZTsgMiBncmVlbiwgMSByZWQiKSkKCihkZWYgdGhyZXNob2xkcyB7OnJlZCAxMiA6Z3JlZW4gMTMgOmJsdWUgMTR9KQoKKGRlZm4gZ2FtZS13aXRoaW4tdGhyZXNob2xkPyBbW19nYW1lLWlkIG1heGVzXV0KICAoLT4%2BIChtZXJnZS13aXRoICMoPj0gJTEgJTIpIHRocmVzaG9sZHMgbWF4ZXMpCiAgICB2YWxzCiAgICAoZXZlcnk%2FIHRydWU%2FKSkpCgooY29tbWVudAogIChnYW1lLXdpdGhpbi10aHJlc2hvbGQ%2FIChnYW1lLW1heGVzICJHYW1lIDE6IDEgZ3JlZW4sIDIgYmx1ZTsgMiBncmVlbiwgMSByZWQiKSkKICApCgooZGVmbiBwb3dlci12YWwgW1tfZ2FtZS1pZCBtYXhlc11dCiAgKC0%2BPiBtYXhlcwogICAgdmFscwogICAgKHJlZHVjZSAjKCogJTEgJTIpKSkpCgooY29tbWVudAogIChwb3dlci12YWwgKGdhbWUtbWF4ZXMgIkdhbWUgMTogMSBncmVlbiwgMiBibHVlOyAyIGdyZWVuLCAxIHJlZCIpKQogICkKCihkZWYgcGFydDEtcmVzdWx0CiAgKC0%2BIChqcy1hd2FpdCAoZmV0Y2gtaW5wdXQgMjAyMyAyKSkKICAgIHN0ci90cmltCiAgICAoc3RyL3NwbGl0ICMiXG4iKQogICAgKC0%2BPiAobWFwdiBnYW1lLW1heGVzKQogICAgICAoZmlsdGVyIGdhbWUtd2l0aGluLXRocmVzaG9sZD8pCiAgICAgIChtYXAgZmlyc3QpCiAgICAgIChyZWR1Y2UgKykpKSkKCihkZWYgcGFydDItcmVzdWx0CiAgKC0%2BIChqcy1hd2FpdCAoZmV0Y2gtaW5wdXQgMjAyMyAyKSkKICAgIHN0ci90cmltCiAgICAoc3RyL3NwbGl0ICMiXG4iKQogICAgKC0%2BPiAobWFwIGdhbWUtbWF4ZXMpCiAgICAgIChtYXAgcG93ZXItdmFsKQogICAgICAocmVkdWNlICspKSkp

πŸ™Œ 1
borkdude 2023-12-02T13:42:44.946669Z

I needed to insert str/trim to get rid of the newline in the input, I wonder why that wasn't a problem in your case

borkdude 2023-12-02T13:44:30.703289Z

ah because it's a difference in squint: user=> (str/split "foo\nbar\n" #"\n") ;;=> [ 'foo', 'bar', '' ] facepalm

Felipe 2023-12-02T13:59:42.724839Z

that was relaxing compared to yesterday https://github.com/FelipeCortez/advent-of-code/blob/master/2023/02.clj

Felipe 2023-12-02T14:03:01.176269Z

@piotr.kaznowski good idea using sorted-map

borkdude 2023-12-02T14:47:02.172119Z

Fixed issues in squint, * and >= etc can now be used as higher order functions and str/split elides empty splitted elements (when limit = nil), like in CLJS Again @larzeitlin’s https://squint-cljs.github.io/squint/?boilerplate=https%3A%2F%2Fgist.githubusercontent.com%2Fborkdude%2Fcf94b492d948f7f418aa81ba54f428ff%2Fraw%2Fa7da6236e9670681a93761b81fd66ad26c119164%2Faoc_ui.cljs&amp;repl=true&amp;src=OzsgSGVscGVyIGZ1bmN0aW9uczoKOzsgKGZldGNoLWlucHV0IHllYXIgZGF5KSAtIGdldCBBT0MgaW5wdXQKOzsgKGFwcGVuZCBzdHIpIC0gYXBwZW5kIHN0ciB0byBET00KOzsgKHNweSB4KSAtIGxvZyB4IHRvIGNvbnNvbGUgYW5kIHJldHVybiB4CgoocmVxdWlyZSAnW2Nsb2p1cmUuc3RyaW5nIDphcyBzdHJdKQoKKGRlZm4gcGFyc2UtY291bnQgW3NdCiAgKGxldCBbW2NudCBjb2xvcl0gKHN0ci9zcGxpdCBzICMiICIpXQogICAgWygjPyg6c3F1aW50IGlkZW50aXR5IDpkZWZhdWx0IGtleXdvcmQpIGNvbG9yKSAocGFyc2UtbG9uZyBjbnQpXSkpCgooY29tbWVudAogIChwYXJzZS1jb3VudCAiMSBncmVlbiIpKQoKKGRlZm4gcGFyc2UtaGFuZCBbc10KICAoLT4%2BIChzdHIvc3BsaXQgcyAjIiwgIikKICAgIChtYXAgcGFyc2UtY291bnQpCiAgICAoaW50byB7fSkpKQoKKGNvbW1lbnQKICAocGFyc2UtaGFuZCAiMSBncmVlbiwgMiBibHVlIikpCgooZGVmbiBnYW1lLW1heGVzIFtzXQogIChsZXQgW1tnYW1lLW5hbWUtc3RyIGNvdW50cy1zdHJdIChzdHIvc3BsaXQgcyAjIjogIikKICAgICAgICBtYXgtY291bnRzICgtPiBjb3VudHMtc3RyCiAgICAgICAgICAgICAgICAgICAgIChzdHIvc3BsaXQgIyI7ICIpCiAgICAgICAgICAgICAgICAgICAgICgtPj4gKG1hcCBwYXJzZS1oYW5kKQogICAgICAgICAgICAgICAgICAgICAgIChhcHBseSBtZXJnZS13aXRoIG1heCkpKQogICAgICAgIGdhbWUtaWQgKC0%2BIGdhbWUtbmFtZS1zdHIgKHN0ci9zcGxpdCAjIiAiKQogICAgICAgICAgICAgICAgICBzZWNvbmQKICAgICAgICAgICAgICAgICAgcGFyc2UtbG9uZyldCiAgICBbZ2FtZS1pZCBtYXgtY291bnRzXSkpCgooY29tbWVudAogIChnYW1lLW1heGVzICJHYW1lIDE6IDEgZ3JlZW4sIDIgYmx1ZTsgMiBncmVlbiwgMSByZWQiKSkKCihkZWYgdGhyZXNob2xkcyB7OnJlZCAxMiA6Z3JlZW4gMTMgOmJsdWUgMTR9KQoKKGRlZm4gZ2FtZS13aXRoaW4tdGhyZXNob2xkPyBbW19nYW1lLWlkIG1heGVzXV0KICAoLT4%2BIChtZXJnZS13aXRoID49IHRocmVzaG9sZHMgbWF4ZXMpCiAgICB2YWxzCiAgICAoZXZlcnk%2FIHRydWU%2FKSkpCgooY29tbWVudAogIChnYW1lLXdpdGhpbi10aHJlc2hvbGQ%2FIChnYW1lLW1heGVzICJHYW1lIDE6IDEgZ3JlZW4sIDIgYmx1ZTsgMiBncmVlbiwgMSByZWQiKSkKICApCgooZGVmbiBwb3dlci12YWwgW1tfZ2FtZS1pZCBtYXhlc11dCiAgKC0%2BPiBtYXhlcwogICAgdmFscwogICAgKHJlZHVjZSAqKSkpCgooY29tbWVudAogIChwb3dlci12YWwgKGdhbWUtbWF4ZXMgIkdhbWUgMTogMSBncmVlbiwgMiBibHVlOyAyIGdyZWVuLCAxIHJlZCIpKQogICkKCihkZWYgcGFydDEtcmVzdWx0CiAgKC0%2BIChqcy1hd2FpdCAoZmV0Y2gtaW5wdXQgMjAyMyAyKSkKICAgIChzdHIvc3BsaXQgIyJcbiIpCiAgICAoLT4%2BIChtYXB2IGdhbWUtbWF4ZXMpCiAgICAgIChmaWx0ZXIgZ2FtZS13aXRoaW4tdGhyZXNob2xkPykKICAgICAgKG1hcCBmaXJzdCkKICAgICAgKHJlZHVjZSArKSkpKQoKKGRlZiBwYXJ0Mi1yZXN1bHQKICAoLT4gKGpzLWF3YWl0IChmZXRjaC1pbnB1dCAyMDIzIDIpKQogICAgKHN0ci9zcGxpdCAjIlxuIikKICAgICgtPj4gKG1hcCBnYW1lLW1heGVzKQogICAgICAobWFwIHBvd2VyLXZhbCkKICAgICAgKHJlZHVjZSArKSkpKQ%3D%3D but essentially the same now except reading the input of course

2023-12-02T14:50:57.685119Z

Nice to put runnable comments for the intermediary steps like this

2023-12-02T15:28:00.451759Z

lol I'm glad ya'll figured out the summing/maxing thing. I was pretty sure I was misinterpreting, but I wasn't' at all sure how.

2023-12-02T15:29:41.010929Z

Fortunately clojure is amazing. (apply merge-with + coll) became (apply merge-with max picks)

2023-12-02T15:34:46.134079Z

re having to rewrite parsing: I've found that lossless parsing really pays off in AoC (and in every day programming as well!)

wevrem 2023-12-02T15:42:43.916969Z

What do you mean, @potetm, by lossless parsing?

2023-12-02T15:43:27.931489Z

"don't throw away any information"

wevrem 2023-12-02T15:43:50.830719Z

And where did you end up using merge-with +?

2023-12-02T15:44:15.789429Z

so, e.g. instead of grabbing the min values from each line, have a parsing phase that grabs all the values

2023-12-02T15:44:26.375409Z

merge-with + was a mistake.

2023-12-02T15:44:44.885159Z

It became merge-with max

πŸ‘ 1
wevrem 2023-12-02T15:50:54.086269Z

I took a gamble and did not do lossless parsing. I think I picked up that trick from @zelark a couple years ago. It paid off this time. I did not keep track of individual sets within each game (which is more effort because the number of sets per game is not fixed), ignored commas and semicolons and just reduced with max. I guess it was lucky that approach worked for both part 1 and part 2. (I had guessed that part 2 would involve some change to the limits, so when it was revealed it was too easy.)

2023-12-02T15:56:20.140589Z

@felipecortezfi yeah, I refactored when the 2nd part was revealed, as it became obvious that only edge cases are important and colors are only needed as "indexes" for unifying data as no further look-ups will follow; then I refactored a bit further, so the solution algorithms accept only vals, not maps.

πŸ‘ 1
Arnaud Geiser 2023-12-02T15:58:57.849819Z

It went quite well today : https://github.com/arnaudgeiser/advent-of-code/blob/master/2023/clojure/src/advent_of_code/day2.clj

πŸ‘ 1
wevrem 2023-12-02T16:03:44.723879Z

I love this ascii art trebuchet.

----@
* ! /^\

Chase 2023-12-02T17:38:20.437209Z

https://github.com/chase-lambert/aoc-clojure/blob/main/src/aoc/2023/day_02.clj Another hacky one for me, I'm excited to check out these more elegant solutions from you folks now

Chase 2023-12-02T17:50:36.020439Z

folks seem reluctant to tackle part 2 so far but I didn't find it that much more difficult than part 1. Could just be early though

Chase 2023-12-02T18:11:19.845539Z

oh man, some of the solutions are so sweet! I feel like my imposter syndrome needs a disclaimer if you spent a good amount of time refactoring to look so nice before posting or is this just naturally how you code off the bat

2023-12-02T18:25:24.634039Z

I would love and "honour-mode" where you get to submit only one solution without running it and you get the star if it passes first time. No repl cheating

2023-12-02T18:25:57.971109Z

I'd be 0/2 this year. coneofshame

2023-12-02T18:26:15.240949Z

Haha likewise

2023-12-02T18:26:22.585539Z

That said, I don't redo anything. I finish and insta commit.

muthui shere 2023-12-02T18:27:39.021699Z

Day 2 seems to be very easy compare to Day 1 (especially part 2). Did a Live Coding used Hyperfiddle for TDD and its available on https://www.youtube.com/watch?v=aF4OfRGnobk . https://github.com/muthuishere/advent-of-code-clojure-2023/blob/main/src/day2.clj

dpsutton 2023-12-02T18:32:44.402069Z

Do you mind deleting this comment? By all means send your live coding to the main channel but don’t put solutions into the channel

dpsutton 2023-12-02T18:32:56.869029Z

And use a snippet for such a long code block

βœ… 1
Jakob Durstberger 2023-12-02T18:36:45.625749Z

I enjoyed day 2. Just parsing colour and count in part 1 turned out to be helpful for the second part. Though reading this thread it would have been nice to know about merge-with https://github.com/JDurstberger/aoc-2023-clj/tree/main/src/day_2 Here is today's video https://youtu.be/Whff9f_BrL8

dpsutton 2023-12-02T18:37:53.815229Z

(And could you please delete the link preview as well? It’s an awesome share just don’t want spoilers leaking out) edit: link previews are fine here in the thread, just don’t want code solutions in the main channel for people who are still solving them)

Cora (she/her) 2023-12-03T02:46:16.773729Z

my day 2 in squint -- didn't use the playground this time due to time constraints (I ended up spending more time working on the playground than doing the actual problems): https://gist.github.com/corasaurus-hex/e800b30d092db6efaaa182aa51d57431

πŸŽ‰ 2
2023-12-02T16:40:18.015619Z

Wanted to make a poll asking people about their approach to AoC questions. Is this not possible in slack without a plugin?

dpsutton 2023-12-02T16:42:13.174389Z

I guess not. I often do things like: How do you do X? β€’ 1️⃣ foo β€’ 2️⃣ bar β€’ 3️⃣ baz and get people to use the emoji reactions 1️⃣ , 2️⃣ , or 3️⃣ and discuss in a thread

1️⃣ 1
πŸ™ 1
βœ… 1
2023-12-02T16:42:41.619659Z

Ah yeah that works

2023-12-02T16:53:48.591329Z

How do you think about performance in your AoC solutions: 1️⃣ Not at all 2️⃣ It's lower priority than some other style / readability considerations 3️⃣ It's an important aspect of my solution - I optimize it intuitively 4️⃣ It's an important aspect of my solution - I measure it 5️⃣ Something else

5️⃣ 2
4️⃣ 2
1️⃣ 14
3️⃣ 1
2️⃣ 24
Ellis 2023-12-02T16:56:20.097499Z

As long as it runs in tens of seconds at most, I'm happy πŸ˜„ Since I compile my clerk notebooks, the solutions run every time I deploy so I need them fast but I'm not too fussed about shaving milliseconds

wevrem 2023-12-02T16:57:08.779269Z

I’m β„– 1 all the time… until you get to that day where it takes 10 million years to solve.

βž• 5
2023-12-02T17:07:12.221229Z

I favour readability over performance for this kind of thing, although I guess readability is a bit subjective

πŸ’― 1
Alvydas Vitkauskas 2023-12-02T17:14:47.390949Z

I did AoC in Clojure last year, and I found that it’s quite easy (for a novice at least) to write correct and (I think) idiomatic Clojure code that runs quite slow. Then you have to think about lazy vs. not-lazy sequences, reflection, boxing etc. I was especially surprised that not-lazy code can be quicker that lazy (as laziness is mostly explained as a mean to save resources and not perform calculations until they are really needed).

πŸ‘ 2
2023-12-02T17:35:35.399429Z

It depends a little on what you're trying to do. Given that I'm only trying to solve the problems, I only care about perf when it matters, and I care about "readability" not a wit πŸ˜„

2023-12-02T17:36:20.526409Z

fwiw I find "readability" to be a grandly misunderstood topic in software, so I'm probably not representative

Cora (she/her) 2023-12-02T17:36:49.159349Z

I do AoC for fun, so I only think of perf when it's fun to or if the solution space my code searches is too large for more naive/fun solutions

βž• 1
Cora (she/her) 2023-12-02T17:38:20.917539Z

this is also probably why I burn out on AoC every year when it hits double digits -- it typically becomes more of a slog at that point and less fun -- I already have a job that challenges me in that way and so my recreation doesn't have to

Chase 2023-12-02T17:46:28.226179Z

I do like to go back and check performance after solving it in my normal hacked up way. I get a little sad when I see my also hacked up Rust code solves it 10x faster with the same lack of initial care. I guess it doesn't mean anything but I wish we could just magically have Clojure be super fast lol (clojure is still 10x more fun to write though of course)

πŸ™Œ 1
2023-12-02T17:50:31.771029Z

@chase-lambert I'm curious to see some side-by-sides. People keep saying rust is great, but my initial take is that it's monstrously complex and forces you to deal with computer tedium. I'd be curious if you came up with relatively straightforward solutions.

Chase 2023-12-02T17:53:06.858119Z

Yeah, for example my first few days of 2015 were written how I normally would do Clojure and Rust I guess. When benchmarking them I see that huge performance gain with Rust. I should probably switch the apply to reduce and whatnot. Caveat: my idiomatic code back in 2015 might just suck in general but that's just when I tried some benchmarking recently https://github.com/chase-lambert/aoc-clojure/tree/main/src/aoc/2015 https://github.com/chase-lambert/aoc_rust/tree/main/aoc_2015/src

2023-12-02T17:55:25.955919Z

This is a great resource! Thank you!

Chase 2023-12-02T17:56:47.877269Z

I'm using this aoc tool called cargo-aoc though because it does the benchmarking for me but it shouldn't make much of a difference I think

Cora (she/her) 2023-12-02T17:57:00.702489Z

Isn't the big trick to making rust easy just doing copy all the time instead of dealing with ownership?

Cora (she/her) 2023-12-02T17:57:07.452449Z

I feel like someone told me that

pez 2023-12-02T17:57:53.248919Z

I care of the performance when it seems like I’d learn something from it.

2023-12-02T18:02:14.109439Z

gah every other language is so clunky after doing clojure for 10 years. I know part of it is just that clojure is near at hand for me, but emotionally it's like watching kids derp around taking 10x the effort for simple tasks.

2023-12-02T18:03:04.114289Z

I mean that in as non-judgemental a way as possible. It's just my emotional (uninformed) reaction.

2023-12-02T18:03:32.415919Z

(Your code is very good btw. Wasn't a comment on that. I can understand it easily. It's the lang, not the writer.)

Chase 2023-12-02T18:04:26.314379Z

Rust definitely gets wild. I find it surprisingly straightforward (once you grok the borrow checker) for regular stuff especially considering how performant it is. It has some nice "high level" features. But when you start really getting into harder tasks, things get crazy quick and I run back to sweet, sweet Clojure.

2023-12-02T18:08:56.347969Z

Did some cryptography puzzles from https://cryptopals.com/ in Rust and found it less painful than i was expecting although I'm pretty sure i was cutting corners in a way that would be considered sloppy by proper rusties

2023-12-02T18:14:33.507619Z

.unwrap() all over the place - tis the season πŸŽ…

πŸ˜‚ 1
oyakushev 2023-12-02T20:18:15.488079Z

I got 50 stars last year with Clojure, and in the second half of the event I was optimizing every solution. This usually comes to: β€’ deftypes instead of maps β€’ arrays and unboxed numbers for anything heavy on the math β€’ iterators and loops instead of map/filter/etc. (this usually counts as a microoptimization and is unnecessary most of the time for AoC tasks) Overall, I'd say that if you picked the right algorithm (one that was intended by Eric for that task), you won't have to think about performance at all. But having a performance-optimized solution sometimes lets you succeed with a suboptimal (from an algorithmic standpoint) approach.

πŸ‘ 1
Cora (she/her) 2023-12-02T19:25:06.626349Z

is the site down for anyone else?

Cora (she/her) 2023-12-02T19:25:14.279339Z

oh, no, it works now

Ellis 2023-12-02T20:03:40.959429Z

Yeah it goes down sometimes, it's just one guy's simple perl site for the most part πŸ˜„

πŸ˜… 1
mauricio.szabo 2023-12-02T23:49:55.518619Z

I decided to try to use Pharo for development, at least to learn about gtoolkit. I am almost giving up - documentation is close to zero, lots of videos (no copy-paste to simplify things), and lots of missing things that I don't even know if it exist (like using capture groups in regexes)