diff --git a/base/namedtuple.jl b/base/namedtuple.jl index 37f3a3ef8436b..57d72bb3ea569 100644 --- a/base/namedtuple.jl +++ b/base/namedtuple.jl @@ -159,7 +159,7 @@ end length(t::NamedTuple) = nfields(t) iterate(t::NamedTuple, iter=1) = iter > nfields(t) ? nothing : (getfield(t, iter), iter + 1) rest(t::NamedTuple) = t -@inline rest(t::NamedTuple{names}, i::Int) where {names} = NamedTuple{rest(names,i)}(t) +@inline rest(t::NamedTuple{names}, i) where {names} = NamedTuple{rest(names,i::Int)}(t) firstindex(t::NamedTuple) = 1 lastindex(t::NamedTuple) = nfields(t) getindex(t::NamedTuple, i::Int) = getfield(t, i) diff --git a/base/tuple.jl b/base/tuple.jl index ebc2cd1e53202..c2c2240296195 100644 --- a/base/tuple.jl +++ b/base/tuple.jl @@ -206,8 +206,12 @@ julia> first, Base.rest(a, state) """ function rest end rest(t::Tuple) = t -rest(t::Tuple, i::Int) = ntuple(x -> getfield(t, x+i-1), length(t)-i+1) -rest(a::Union{Array,Memory,Core.SimpleVector}, i::Int=1) = a[i:end] +function rest(t::Tuple, i) + let i = i::Int + ntuple(x -> getfield(t, x+i-1), length(t)-i+1) + end +end +rest(a::Union{Array,Memory,Core.SimpleVector}, i=1) = a[(i::Int):end] rest(itr, state...) = Iterators.rest(itr, state...) """ diff --git a/test/core.jl b/test/core.jl index 84444ecb725d7..004a352f5f75f 100644 --- a/test/core.jl +++ b/test/core.jl @@ -8193,6 +8193,25 @@ foo46503(a::Int, b::Nothing) = @invoke foo46503(a::Any, b) foo46503(@nospecialize(a), b::Union{Nothing, Float64}) = rand() + 10 @test 10 <= foo46503(1, nothing) <= 11 +@testset "inference for `rest` with unknown state argument types" begin + @testset "`Array`, `Memory`" begin + for typ in (Vector{Float32}, Matrix{Float32}, Memory{Float32}) + @test (isconcretetype ∘ Base.infer_return_type)(Base.rest, Tuple{typ, Any}) + for e in (Base.Compiler.is_terminates, Base.Compiler.is_notaskstate, Base.Compiler.is_nonoverlayed) + @test (e ∘ Base.infer_effects)(Base.rest, Tuple{typ, Any}) + end + end + end + @testset "`Tuple`" begin + typ = NTuple{5, Float32} + @test Base.infer_return_type(Base.rest, Tuple{typ, Any}) <: Tuple + end + @testset "`NamedTuple`" begin + typ = NamedTuple{(:a, :b, :c, :d, :e), NTuple{5, Float32}} + @test Base.infer_return_type(Base.rest, Tuple{typ, Any}) <: NamedTuple + end +end + @testset "effect override on Symbol(::String)" begin @test Core.Compiler.is_foldable(Base.infer_effects(Symbol, (String,))) end