diff --git a/base/missing.jl b/base/missing.jl index e1988064aadc1..5a8563e2bb1d3 100644 --- a/base/missing.jl +++ b/base/missing.jl @@ -246,6 +246,8 @@ IteratorSize(::Type{<:SkipMissing}) = SizeUnknown() IteratorEltype(::Type{SkipMissing{T}}) where {T} = IteratorEltype(T) eltype(::Type{SkipMissing{T}}) where {T} = nonmissingtype(eltype(T)) +length(s::SkipMissing{T}) where T <: AbstractArray = count(!ismissing, s.x) + function iterate(itr::SkipMissing, state...) y = iterate(itr.x, state...) y === nothing && return nothing diff --git a/test/missing.jl b/test/missing.jl index 13ed684f1fc05..70bf3df154a04 100644 --- a/test/missing.jl +++ b/test/missing.jl @@ -441,6 +441,20 @@ end @test collect(x) == [1, 2, 4] @test collect(x) isa Vector{Int} + @testset "length" begin + allmiss = Vector{Union{Int,Missing}}(missing, 10) + @test (length∘skipmissing)(allmiss) == 0 + + somemiss = [1, missing, 2, 3, 4, missing, 5, 6, 7, 8, 9, 10] + @test (length∘skipmissing)(somemiss) == 10 + + nomiss = rand(1:10, 10) + @test (length∘skipmissing)(nomiss) == 10 + + itr = Iterators.Stateful([missing, 1, missing, 1]) + @test_throws MethodError (length∘skipmissing)(itr) + end + @testset "indexing" begin x = skipmissing([1, missing, 2, missing, missing]) @test collect(eachindex(x)) == collect(keys(x)) == [1, 3]