Call FastClosures.jl `@closure` in Array Comprehensions?

uniment
Fri, 27 Jan 2023 11:03:34 +0000
Internals & Design

Like with any closure, array comprehensions present a performance challenge if they capture a variable whose identifier is reassigned:

julia> using BenchmarkTools

julia> const a=[1:1000;];

julia> @btime let b=a; [b[x] for x ∈ b] end;
  436.224 ns (1 allocation: 7.94 KiB)

julia> @btime let b=a; b=b; [b[x] for x ∈ b] end;
  23.000 μs (984 allocations: 23.33 KiB)

julia> @btime let b=a; c=b; [c[x] for x ∈ c] end;
  412.366 ns (1 allocation: 7.94 KiB)

Unlike generators, comprehensions offer syntactical assurance that the closure will be executed and consumed immediately—so there’s no reason to box the captures. Additionally, the use of a lambda is just an implementation detail, which adds surprise when someone new to Julia is confronted with this performance degradation.

Would it then make sense for Julia to use the FastClosures.jl @closure macro to prevent boxing here, as recommended in the performance manual?

3 posts - 2 participants