Skip to content

Commit

Permalink
improve REPL printing of sets (JuliaLang#33300)
Browse files Browse the repository at this point in the history
  • Loading branch information
rfourquet authored and StefanKarpinski committed Oct 30, 2019
1 parent b92a35d commit 306182f
Show file tree
Hide file tree
Showing 6 changed files with 90 additions and 13 deletions.
2 changes: 2 additions & 0 deletions NEWS.md
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,8 @@ Standard library changes

* Verbose `display` of `Char` (`text/plain` output) now shows the codepoint value in standard-conforming `"U+XXXX"` format ([#33291]).

* Sets are now displayed less compactly in the REPL, as a column of elements, like vectors
and dictionaries ([#33300]).

#### Libdl

Expand Down
18 changes: 14 additions & 4 deletions base/abstractset.jl
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,10 @@ julia> union([4, 2], 1:2)
1
julia> union(Set([1, 2]), 2:3)
Set([2, 3, 1])
Set{Int64} with 3 elements:
2
3
1
```
"""
function union end
Expand All @@ -60,7 +63,12 @@ julia> a = Set([1, 3, 4, 5]);
julia> union!(a, 1:2:8);
julia> a
Set([7, 4, 3, 5, 1])
Set{Int64} with 5 elements:
7
4
3
5
1
```
"""
function union!(s::AbstractSet, sets...)
Expand Down Expand Up @@ -105,7 +113,8 @@ julia> intersect([1, 4, 4, 5, 6], [4, 6, 6, 7, 8])
6
julia> intersect(Set([1, 2]), BitSet([2, 3]))
Set([2])
Set{Int64} with 1 element:
2
```
"""
intersect(s::AbstractSet, itr, itrs...) = intersect!(intersect(s, itr), itrs...)
Expand Down Expand Up @@ -160,7 +169,8 @@ julia> a = Set([1, 3, 4, 5]);
julia> setdiff!(a, 1:2:6);
julia> a
Set([4])
Set{Int64} with 1 element:
4
```
"""
function setdiff!(s::AbstractSet, itrs...)
Expand Down
7 changes: 5 additions & 2 deletions base/array.jl
Original file line number Diff line number Diff line change
Expand Up @@ -1076,13 +1076,16 @@ julia> A
2
julia> S = Set([1, 2])
Set([2, 1])
Set{Int64} with 2 elements:
2
1
julia> pop!(S)
2
julia> S
Set([1])
Set{Int64} with 1 element:
1
julia> pop!(Dict(1=>2))
1 => 2
Expand Down
9 changes: 7 additions & 2 deletions base/set.jl
Original file line number Diff line number Diff line change
Expand Up @@ -439,7 +439,10 @@ julia> replace!([1, 2, 1, 3], 1=>0, 2=>4, count=2)
3
julia> replace!(Set([1, 2, 3]), 1=>0)
Set([0, 2, 3])
Set{Int64} with 3 elements:
0
2
3
```
"""
replace!(A, old_new::Pair...; count::Integer=typemax(Int)) =
Expand Down Expand Up @@ -479,7 +482,9 @@ Dict{Int64,Int64} with 2 entries:
1 => 3
julia> replace!(x->2x, Set([3, 6]))
Set([6, 12])
Set{Int64} with 2 elements:
6
12
```
"""
replace!(new::Callable, A; count::Integer=typemax(Int)) =
Expand Down
47 changes: 46 additions & 1 deletion base/show.jl
Original file line number Diff line number Diff line change
Expand Up @@ -113,7 +113,10 @@ function show(io::IO, ::MIME"text/plain", t::AbstractDict{K,V}) where {K,V}

for (i, (k, v)) in enumerate(t)
print(io, "\n ")
i == rows < length(t) && (print(io, rpad("", keylen), " => ⋮"); break)
if i == rows < length(t)
print(io, rpad("", keylen), " => ⋮")
break
end

if limit
key = rpad(_truncate_at_width_or_chars(ks[i], keylen, "\r\n"), keylen)
Expand All @@ -132,6 +135,48 @@ function show(io::IO, ::MIME"text/plain", t::AbstractDict{K,V}) where {K,V}
end
end

function summary(io::IO, t::AbstractSet)
n = length(t)
showarg(io, t, true)
print(io, " with ", n, (n==1 ? " element" : " elements"))
end

function show(io::IO, ::MIME"text/plain", t::AbstractSet{T}) where T
# show more descriptively, with one line per value
recur_io = IOContext(io, :SHOWN_SET => t)
limit::Bool = get(io, :limit, false)

summary(io, t)
isempty(t) && return
print(io, ":")
show_circular(io, t) && return
if limit
sz = displaysize(io)
rows, cols = sz[1] - 3, sz[2]
rows < 2 && (print(io, ""); return)
cols -= 2 # Subtract the width of prefix " "
cols < 4 && (cols = 4) # Minimum widths of 4 for value
rows -= 1 # Subtract the summary
else
rows = cols = typemax(Int)
end

for (i, v) in enumerate(t)
print(io, "\n ")
if i == rows < length(t)
print(io, rpad("", 2))
break
end

if limit
str = sprint(show, v, context=recur_io, sizehint=0)
print(io, _truncate_at_width_or_chars(str, cols, "\r\n"))
else
show(recur_io, v)
end
end
end

function show(io::IO, ::MIME"text/plain", opt::JLOptions)
println(io, "JLOptions(")
fields = fieldnames(JLOptions)
Expand Down
20 changes: 16 additions & 4 deletions test/show.jl
Original file line number Diff line number Diff line change
Expand Up @@ -456,9 +456,6 @@ let a = Expr(:quote,Expr(:$,:x8d003))
@test eval(eval(Meta.parse(repr(a)))) == 2
end

# issue #9865
@test occursin(r"^Set\(\[.+….+\]\)$", replstr(Set(1:100)))

# issue #11413
@test string(:(*{1, 2})) == "*{1, 2}"
@test string(:(*{1, x})) == "*{1, x}"
Expand Down Expand Up @@ -1278,7 +1275,7 @@ end
@test replstr(view(A, [1], :)) == "1×1 view(::Array{Float64,2}, [1], :) with eltype Float64:\n 0.0"

# issue #27680
@test replstr(Set([(1.0,1.0), (2.0,2.0), (3.0, 3.0)])) == (sizeof(Int) == 8 ?
@test showstr(Set([(1.0,1.0), (2.0,2.0), (3.0, 3.0)])) == (sizeof(Int) == 8 ?
"Set([(3.0, 3.0), (2.0, 2.0), (1.0, 1.0)])" :
"Set([(1.0, 1.0), (2.0, 2.0), (3.0, 3.0)])")

Expand Down Expand Up @@ -1589,6 +1586,21 @@ end
@test sdastr(3, 3) == "[3, 4, 5]"
end

@testset "show Set" begin
s = Set{Int}(1:22)
str = showstr(s)
@test startswith(str, "Set([")
@test endswith(str, "])")
@test occursin("", str)

str = replstr(s)
@test startswith(str, "Set{$Int} with 22 elements:\n")
@test endswith(str, "\n")
@test count(==('\n'), str) == 20

@test replstr(Set(['a'^100])) == "Set{String} with 1 element:\n \"aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa…"
end

@testset "0-dimensional Array. Issue #31481" begin
for x in (zeros(Int32), collect('b'), fill(nothing), BitArray(0))
@test eval(Meta.parse(repr(x))) == x
Expand Down

0 comments on commit 306182f

Please sign in to comment.