Using in-combinations makes things a bit cleaner (and faster, I suspect), which would've been useful on day 8 as well, but I had forgotten about it.
Spoilers
; day 9
; part 1
(for/fold ([best -inf.0])
([pair (in-combinations red-tiles 2)])
(max best (apply area pair)))
; part 2
(for/fold ([best -inf.0])
([pair (in-combinations red-tiles 2)]
#:do [(define r (apply bounds pair))]
#:when (andmap in-polygon? (rectangle-frame r))
#:unless (bisected? (rectangle-around? r)))
(max best (rectangle-area r)))
; day 8
(define pairwise-distances
(sort
#:key car
(for/list ([pair (in-combinations junctions 2)])
(cons (apply distance pair) pair))
<))
As an aside, I started using complex numbers because I thought they would be useful when calculating areas, but I couldn't quite get the calculations to work, so I ended up deconstructing them anyhow. They were useful for the interpolation, though, which was fortunate.
Edit: I realized the area comparison could be reordered to speed it up a bit.
Spoilers
(time
(for/fold ([best -inf.0])
([pair (in-combinations red-tiles 2)]
#:do [(define r (apply bounds pair))]
#:when (< best (rectangle-area r))
#:when (andmap in-hull? (rectangle-corners r))
#:unless (hull-bisects? (rectangle-contains? r)))
(rectangle-area r)))
;=> cpu time: 1343 real time: 1383 gc time: 468
Although this doesn't show the optimization for interpolated points, which I also realized only really needed to be calculated once.