Skip to content

Commit

Permalink
Rename IndexValue -> Pairs, print it better
Browse files Browse the repository at this point in the history
As discussed in #25711

Before:
```
julia> f(;kwargs...) = kwargs
f (generic function with 1 method)

julia> f(;a = 1, b = 2)
Base.Iterators.IndexValue{Symbol,Int64,Tuple{Symbol,Symbol},NamedTuple{(:a, :b),Tuple{Int64,Int64}}} with 2 entries:
  :a => 1
  :b => 2
```

After:
```
julia> f(;a = 1, b = 2)
pairs((a = 1, b = 2)) with 2 entries:
  :a => 1
  :b => 2
```
  • Loading branch information
Keno committed Jan 26, 2018
1 parent 7d3991f commit 043cb8e
Show file tree
Hide file tree
Showing 5 changed files with 44 additions and 31 deletions.
5 changes: 3 additions & 2 deletions base/abstractdict.jl
Original file line number Diff line number Diff line change
Expand Up @@ -30,9 +30,10 @@ function in(p, a::AbstractDict)
function if you are looking for a key or value respectively.""")
end

function summary(t::AbstractDict)
function summary(io::IO, t::AbstractDict)
n = length(t)
return string(typeof(t), " with ", n, (n==1 ? " entry" : " entries"))
showarg(io, t, true)
print(io, " with ", n, (n==1 ? " entry" : " entries"))
end

struct KeySet{K, T <: AbstractDict{K}} <: AbstractSet{K}
Expand Down
4 changes: 4 additions & 0 deletions base/essentials.jl
Original file line number Diff line number Diff line change
Expand Up @@ -765,3 +765,7 @@ Indicate whether `x` is [`missing`](@ref).
"""
ismissing(::Any) = false
ismissing(::Missing) = true

# forward declarations for use by iterators.jl (since parts of that file
# are used by the compiler)
function showarg end
60 changes: 34 additions & 26 deletions base/iterators.jl
Original file line number Diff line number Diff line change
Expand Up @@ -152,15 +152,23 @@ end
@inline done(r::Reverse{<:Enumerate}, state) = state[1] < 1

"""
Iterators.IndexValue(values, keys) <: AbstractDict{eltype(keys), eltype(values)}
Iterators.Pairs(values, keys) <: AbstractDict{eltype(keys), eltype(values)}
Transforms an indexable container into an Dictionary-view of the same data.
Modifying the key-space of the underlying data may invalidate this object.
"""
struct IndexValue{K, V, I, A} <: AbstractDict{K, V}
struct Pairs{K, V, I, A} <: AbstractDict{K, V}
data::A
itr::I
IndexValue(data::A, itr::I) where {A, I} = new{eltype(I), eltype(A), I, A}(data, itr)
Pairs(data::A, itr::I) where {A, I} = new{eltype(I), eltype(A), I, A}(data, itr)
end

function Base.showarg(io::IO, r::Pairs, toplevel)
if try typeof(pairs(r.data)) == typeof(r); catch; false; end
print(io, "pairs(", r.data, ")")
else
print(io, "Iterators.Pairs(",r.data, ", ", r.itr,")")
end
end

"""
Expand Down Expand Up @@ -209,42 +217,42 @@ CartesianIndex(2, 2) e
See also: [`IndexStyle`](@ref), [`axes`](@ref).
"""
pairs(::IndexLinear, A::AbstractArray) = IndexValue(A, linearindices(A))
pairs(::IndexCartesian, A::AbstractArray) = IndexValue(A, CartesianIndices(axes(A)))
pairs(::IndexLinear, A::AbstractArray) = Pairs(A, linearindices(A))
pairs(::IndexCartesian, A::AbstractArray) = Pairs(A, CartesianIndices(axes(A)))

# preserve indexing capabilities for known indexable types
# faster than zip(keys(a), values(a)) for arrays
pairs(A::AbstractArray) = pairs(IndexCartesian(), A)
pairs(A::AbstractVector) = pairs(IndexLinear(), A)
pairs(tuple::Tuple) = IndexValue(tuple, keys(tuple))
pairs(nt::NamedTuple) = IndexValue(nt, keys(nt))
# pairs(v::IndexValue) = v # listed for reference, but already defined from being an AbstractDict

length(v::IndexValue) = length(v.itr)
axes(v::IndexValue) = axes(v.itr)
size(v::IndexValue) = size(v.itr)
@inline start(v::IndexValue) = start(v.itr)
@propagate_inbounds function next(v::IndexValue, state)
pairs(tuple::Tuple) = Pairs(tuple, keys(tuple))
pairs(nt::NamedTuple) = Pairs(nt, keys(nt))
# pairs(v::Pairs) = v # listed for reference, but already defined from being an AbstractDict

length(v::Pairs) = length(v.itr)
axes(v::Pairs) = axes(v.itr)
size(v::Pairs) = size(v.itr)
@inline start(v::Pairs) = start(v.itr)
@propagate_inbounds function next(v::Pairs, state)
indx, n = next(v.itr, state)
item = v.data[indx]
return (Pair(indx, item), n)
end
@inline done(v::IndexValue, state) = done(v.itr, state)
@inline done(v::Pairs, state) = done(v.itr, state)

eltype(::Type{IndexValue{K, V}}) where {K, V} = Pair{K, V}
eltype(::Type{Pairs{K, V}}) where {K, V} = Pair{K, V}

IteratorSize(::Type{IndexValue{<:Any, <:Any, I}}) where {I} = IteratorSize(I)
IteratorEltype(::Type{IndexValue{<:Any, <:Any, I}}) where {I} = IteratorEltype(I)
IteratorSize(::Type{Pairs{<:Any, <:Any, I}}) where {I} = IteratorSize(I)
IteratorEltype(::Type{Pairs{<:Any, <:Any, I}}) where {I} = IteratorEltype(I)

reverse(v::IndexValue) = IndexValue(v.data, reverse(v.itr))
reverse(v::Pairs) = Pairs(v.data, reverse(v.itr))

haskey(v::IndexValue, key) = (key in v.itr)
keys(v::IndexValue) = v.itr
values(v::IndexValue) = v.data
getindex(v::IndexValue, key) = v.data[key]
setindex!(v::IndexValue, value, key) = (v.data[key] = value; v)
get(v::IndexValue, key, default) = get(v.data, key, default)
get(f::Base.Callable, collection::IndexValue, key) = get(f, v.data, key)
haskey(v::Pairs, key) = (key in v.itr)
keys(v::Pairs) = v.itr
values(v::Pairs) = v.data
getindex(v::Pairs, key) = v.data[key]
setindex!(v::Pairs, value, key) = (v.data[key] = value; v)
get(v::Pairs, key, default) = get(v.data, key, default)
get(f::Base.Callable, collection::Pairs, key) = get(f, v.data, key)

# zip

Expand Down
4 changes: 2 additions & 2 deletions doc/src/base/collections.md
Original file line number Diff line number Diff line change
Expand Up @@ -225,7 +225,7 @@ Partially implemented by:
* [`Array`](@ref)
* [`BitArray`](@ref)
* [`ImmutableDict`](@ref Base.ImmutableDict)
* [`Iterators.IndexValue`](@ref)
* [`Iterators.Pairs`](@ref)

## Set-Like Collections

Expand Down Expand Up @@ -276,5 +276,5 @@ Fully implemented by:

```@docs
Base.Pair
Iterators.IndexValue
Iterators.Pairs
```
2 changes: 1 addition & 1 deletion test/iterators.jl
Original file line number Diff line number Diff line change
Expand Up @@ -431,7 +431,7 @@ end
@test eltype(arr) == Int
end

@testset "IndexValue type" begin
@testset "Pairs type" begin
for A in ([4.0 5.0 6.0],
[],
(4.0, 5.0, 6.0),
Expand Down

0 comments on commit 043cb8e

Please sign in to comment.