Normally zip
will stop if any component reaches end. e.g.,
julia> for (a,b) in zip(1:2,3)
println("$a,$b")
end
1,3
If I want it to align with the longest component (the shorter components just repeat), then have to write as
julia> for (a,b) in zip(1:2,cycle(3))
println("$a,$b")
end
1,3
2,3
My question is, is there any dedicated function for doing this latter task?
You can always define your own, but zip(x, [Iterators.]cycle(y))
is pretty simple already.
1 Like
Okay, good to know that. It turns out to be a one-line thing
julia> zip_align_first(a,b...) = zip(a, cycle.([b...])...)
zip_align_first (generic function with 1 method)
julia> collect(zip_align_first(1:6, 3, 4, [5,6], [7,8,9]))
6-element Array{Tuple{Int64,Int64,Int64,Int64,Int64},1}:
(1,3,4,5,7)
(2,3,4,6,8)
(3,3,4,5,9)
(4,3,4,6,7)
(5,3,4,5,8)
(6,3,4,6,9)
You could also sort the arguments before zipping. That way, you do not need to pass the longest argument first:
julia> function zip_align(args...)
sorted = sort([args...],by=x->-length(x))
zip(sorted[1],cycle.(sorted[2:end])...)
end
zip_align (generic function with 1 method)
julia> collect(zip_align([1,2,3],[4,5],[6,7,8,9,10]))
5-element Array{Tuple{Int64,Int64,Int64},1}:
(6,1,4)
(7,2,5)
(8,3,4)
(9,1,5)
(10,2,4)
1 Like