diff options
Diffstat (limited to 'day15/part2.clj')
-rw-r--r-- | day15/part2.clj | 56 |
1 files changed, 28 insertions, 28 deletions
diff --git a/day15/part2.clj b/day15/part2.clj index d48ba92..1b2b409 100644 --- a/day15/part2.clj +++ b/day15/part2.clj @@ -1,3 +1,5 @@ +(require '[clojure.core.reducers :as r]) + (def input (->> (slurp "./in") (clojure.string/split-lines) (mapv (partial mapv (comp read-string str))) @@ -17,15 +19,16 @@ )) (defn min-distance [dist Q] - (reduce - #(if (and (not= (dist %2) :inf) - (or (= :inf (first %1)) - (< (dist %2) (first %1)))) - [(dist %2) %2] - %1) - [:inf []] - Q - )) + (r/fold + (r/monoid + #(if (< (first %1) (first %2)) %1 %2) + (constantly [##Inf []])) + (r/monoid + #(if (< (first %1) (dist %2)) %1 [(dist %2) %2]) + (constantly [##Inf []])) + (r/filter + (partial contains? dist) + (apply vector Q)))) (defn find-neighbors [Q u] (filter #(contains? Q %) [(update u 0 inc) @@ -33,22 +36,19 @@ (update u 1 inc) (update u 1 dec)])) -(loop [Q (set (keys input)) - dist (-> (zipmap Q (repeat :inf)) (update [0 0] #(do % 0)))] - (if (empty? Q) - (println (dist [499 499])) - (let [[u vu] (min-distance dist Q)] - (recur - (disj Q vu) - (loop [d dist f (find-neighbors Q vu)] - (if (empty? f) - d - (recur - (let [v (first f) alt (+ u (input v))] - (if (or (= :inf (dist v)) (< alt (dist v))) - (assoc d v alt) - d - )) - (rest f) - ))))))) - +(let [dim (apply max (map first (keys input)))] + (loop [Q (apply sorted-set (keys input)) + dist (assoc (hash-map) [0 0] 0)] + (when (= 0 (rem (count Q) 500)) (println (count Q))) + (if (empty? Q) + (println (dist [dim dim])) + (let [[u vu] (min-distance dist Q)] + (recur + (disj Q vu) + (reduce + #(let [alt (+ u (input %2))] + (cond-> %1 + (or (not (contains? dist %2)) (< alt (dist %2))) + (assoc %2 alt))) + dist + (find-neighbors Q vu))))))) |