Clojure, 227227 198 bytes
(fn[t w h](let[elet[c #(for[y(range %3 %4)x(range % %2)][x y])e #(= 8(get-in t(reverse %)0))m(fn[[o p]](reducecount(fn [nfilter c](if(e c)(inc n)n))0(for[y(rangec(dec po)(+ po 2))x(range(dec op)(+ op 2))][x y])))](->> count(for[yfilter #(range= h)x1(rangem w%)][x y])(filter e)(filterc #(=0 1(mw %)0 h))(count))))
Ouch. Definitely not the shortest here by any means. 54 bytes of parenthesis is killer. I'm still relatively happy with it though. I think I could probably make
-29 bytes by creating a couple "shortcuts"helper function that reduce some duplication and get rid ofgenerates a range since I was doing that twice, changing the need for reduce
to a (count (filter
setup, but I doubt I'mand getting much better than 200 bytesrid of the threading macro after golfing.
(defn count-single-eights [td-array width height]
; Define twothree helpers. One generates a list of coords for a given range of dimensions, another checks if an eight is
; at the given coord,
; and the other counts how many neighbors around a coord are an eight
(letfn [(eight? [[x y]] (= 8coords (get[x-inmin tdx-array [y x] 0)))
max (n-eightsy-around [[cxmin cy]]y-max]
(reduce (fn [n coord]
for [y (ifrange (eight?y-min coordy-max)
x (incrange nx-min x-max)]
[x ny]))
(eight? [[x y]] (= 8 (get-in td-array [y x] 0)))
(n-eights-around [[cx cy]]
(for [y (range (dec cy)count (+ cyfilter 2))eight?
x (rangecoords (dec cx) (+ cx 2))]
, (dec cy) (+ [xcy y]2)))))]
; Gen a list of each coord of the matrix
(->> (for [y (range height)
xcoords (range0 width)]
, [x0 y]height)
; Remove any coords that don't contain an eight
(filter eight?)
; Then count how many "neighborhoods" only contain 1 eight
(filter #(= 1 (n-eights-around %)))
(count))))
(mapv #(count-single-eights % (count (% 0)) (count %))
test-cases)
=> [3 0 0 2 2 1 3 1 4 3]
Try it online!Try it online!