Vector of Vectors with different size to one Vector

I am sorry for the easy questions.
Would you suggest how to convert:
Vector of Vectors with different size to one Vector

julia> reduce(vcat, [[1,2,3], [4, 5], [6]])
6-element Array{Int64,1}:
 1
 2
 3
 4
 5
 6

For more information, check out ?reduce and ?vcat.

1 Like

Thank you so much

vcat accepts “varargs”, so reduce isn’t needed:

vv = [rand(x) for x in 1:100]
vcat(vv...)

Splatting is a lot less efficient. Use reduce

2 Likes

Ah didn’t realize that. It is indeed slower for a small number of vectors, but the relative difference decreases as the number grows:


julia> vv = [rand(x) for x in 1:10];

julia> @btime vcat($vv...);
  152.276 ns (1 allocation: 544 bytes)

julia> @btime reduce(vcat, $vv);
  72.192 ns (1 allocation: 544 bytes)

julia> vv = [rand(x) for x in 1:10^4];

julia> @btime vcat($vv...);
  113.653 ms (3 allocations: 381.58 MiB)

julia> @btime reduce(vcat, $vv);
  113.678 ms (2 allocations: 381.51 MiB)

As an aside, reduce may be slower with generators.

julia> a = (rand(100) for i=1:100);

julia> @btime reduce(hcat,$a);
  689.859 μs (380 allocations: 3.95 MiB)

julia> @btime hcat($a...);
  67.084 μs (210 allocations: 172.09 KiB)

Perhaps this is because the type inference doesn’t lead to a concrete type.

julia> @code_warntype reduce(hcat,a)
Variables
  #self#::Core.Compiler.Const(reduce, false)
  op::Core.Compiler.Const(hcat, false)
  itr::Base.Generator{UnitRange{Int64},var"#26#27"}

Body::Array
1 ─ %1 = Core.NamedTuple()::Core.Compiler.Const(NamedTuple(), false)
│   %2 = Base.pairs(%1)::Core.Compiler.Const(Base.Iterators.Pairs{Union{},Union{},Tuple{},NamedTuple{(),Tuple{}}}(), false)
│   %3 = Base.:(var"#reduce#195")(%2, #self#, op, itr)::Array
└──      return %3
1 Like

A comprehension also works.

 julia> let vofv = [[1,2,3], [4,5], [6]]
          [y for v in vofv for y in v]
        end
 6-element Array{Int64,1}:
  1
  2
  3
  4
  5
  6

Yes, but collecting a and reducing it is even faster.

julia> f(x) = reduce(hcat, collect(x))
f (generic function with 1 method)

julia> @btime f($a);
  31.211 μs (103 allocations: 166.58 KiB)

julia> @btime hcat($a...);
  49.138 μs (210 allocations: 172.09 KiB)
1 Like

The “proper” answer really depends on what you are planning on doing with the result. If the desire is simply to iterate over each element in turn you may want to consider something like Iterators.flatten, for example

1 Like