From 99756bcc701726bddaf6bd4fc0351767270704b8 Mon Sep 17 00:00:00 2001 From: Rafael Schouten Date: Sun, 8 Sep 2019 17:32:03 +1000 Subject: [PATCH] fix reverse performance, cleanup for code cov --- src/array.jl | 15 +++++++++++---- src/dimension.jl | 8 +------- src/interface.jl | 9 ++++++++- test/runtests.jl | 24 ++++++++++++++---------- 4 files changed, 34 insertions(+), 22 deletions(-) diff --git a/src/array.jl b/src/array.jl index 0a11e2eee..8c731fc79 100644 --- a/src/array.jl +++ b/src/array.jl @@ -70,7 +70,6 @@ Base.similar(bc::Broadcast.Broadcasted{Broadcast.ArrayStyle{AbDimArray}}, ::Type # these aren't usefull unless you inherit from AbDimArray. Base.mapslices(f, a::AbDimArray; dims=1, kwargs...) = begin - println((f, dims, dimnum(a, dims))) dimnums = dimnum(a, dims) data = mapslices(f, parent(a); dims=dimnums, kwargs...) rebuildsliced(a, data, dims2indices(a, reducedims(DimensionalData.dims(a, dimnums)))) @@ -100,15 +99,23 @@ for fname in (:cor, :cov) end end -Base.reverse(a::AbDimArray{T,N}; dims=1) where {T,N} = begin +@inline Base.reverse(a::AbDimArray{T,N}; dims=1) where {T,N} = begin dnum = dimnum(a, dims) # Reverse the dimension. TODO: make this type stable - newdims = Tuple(map((x, n) -> n == dnum ? basetype(x)(reverse(val(x))) : x, DimensionalData.dims(a), 1:N)) + newdims = revdims(DimensionalData.dims(a), dnum) # Reverse the data newdata = reverse(parent(a); dims=dnum) rebuild(a, newdata, newdims, refdims(a)) end +@inline revdims(dimstorev::Tuple, dnum) = begin + dim = dimstorev[end] + if length(dimstorev) == dnum + dim = rebuild(dim, reverse(val(dim))) + end + (revdims(Base.front(dimstorev), dnum)..., dim) +end +@inline revdims(dims::Tuple{}, i) = () """ @@ -128,7 +135,7 @@ DimensionalArray(a::AbstractArray, dims; refdims=()) = Base.parent(a::DimensionalArray) = a.data # DimensionalArray interface -rebuild(a::DimensionalArray, data, dims, refdims) = +@inline rebuild(a::DimensionalArray, data, dims, refdims) = DimensionalArray(data, dims, refdims) refdims(a::DimensionalArray) = a.refdims diff --git a/src/dimension.jl b/src/dimension.jl index 62b5fab51..792df7c5e 100644 --- a/src/dimension.jl +++ b/src/dimension.jl @@ -48,18 +48,11 @@ rebuild(dim::AbDim, val) = basetype(dim)(val, metadata(dim), order(dim)) dims(x::AbDim) = x dims(x::AbDimTuple) = x - -name(dims::AbDimTuple) = (name(dims[1]), name(tail(dims))...) -name(dims::Tuple{}) = () name(dim::AbDim) = name(typeof(dim)) - shortname(d::AbDim) = shortname(typeof(d)) shortname(d::Type{<:AbDim}) = name(d) - units(dim::AbDim) = metadata(dim) == nothing ? "" : get(metadata(dim), :units, "") -label(dims::AbDimTuple) = join(join.(zip(name.(dims), string.(shorten.(val.(dims)))), ": ", ), ", ") - bounds(a, args...) = bounds(dims(a), args...) bounds(dims::AbDimTuple, lookupdims::Tuple) = bounds(dims[[dimnum(dims, lookupdims)...]]) bounds(dims::AbDimTuple, dim::DimOrDimType) = bounds(dims[dimnum(dims, dim)]) @@ -174,6 +167,7 @@ end @inline Dim{X}(val=:; metadata=nothing, order=Forward()) where X = Dim{X}(val, metadata, order) name(::Type{<:Dim{X}}) where X = "Dim $X" +shortname(::Type{<:Dim{X}}) where X = "$X" basetype(::Type{<:Dim{X,T,N}}) where {X,T,N} = Dim{X} diff --git a/src/interface.jl b/src/interface.jl index 2ef06b2a1..8c9153f87 100644 --- a/src/interface.jl +++ b/src/interface.jl @@ -62,6 +62,7 @@ Return the units of a dimension. This could be a string, a unitful unit, or noth """ function units end units(x) = "" +units(xs::Tuple) = map(units, xs) """ name(x) @@ -71,6 +72,7 @@ Get the name of data or a dimension. function name end name(x) = name(typeof(x)) name(x::Type) = "" +name(xs::Tuple) = map(name, xs) """ shortname(x) @@ -79,6 +81,7 @@ Get the short name of array data or a dimension. """ function shortname end shortname(x) = shortname(typeof(x)) +shortname(xs::Tuple) = map(shortname, xs) shortname(x::Type) = "" """ @@ -88,4 +91,8 @@ Get a plot label for data or a dimension. This will include the name and units if they exist, and anything else that should be shown on a plot. """ function label end -label(x) = string(string(name(x)), " ", getstring(units(x))) +label(x) = begin + u = getstring(units(x)) + string(name(x), (u == "" ? "" : string(" ", u))) +end +label(xs::Tuple) = join(map(label, xs), ", ") diff --git a/test/runtests.jl b/test/runtests.jl index b50a706c0..1d3421af9 100644 --- a/test/runtests.jl +++ b/test/runtests.jl @@ -12,8 +12,7 @@ using DimensionalData: val, basetype, slicedims, dims2indices, formatdims, @test val(TestDim(:test)) == :test @test metadata(TestDim(1, "metadata", Forward())) == "metadata" @test units(TestDim) == "" -# TODO get rid of the trailing whitespace -@test_broken label(TestDim) == "Test dimension" +@test label(TestDim) == "Test dimension" @test eltype(TestDim(1)) == Int @test eltype(TestDim([1,2,3])) == Vector{Int} @test length(TestDim(1)) == 1 @@ -26,6 +25,10 @@ a = ones(5, 4) da = DimensionalArray(a, (X((140, 148)), Y((2, 11)))) dimz = dims(da) @test slicedims(dimz, (2:4, 3)) == ((X(LinRange(142,146,3)),), (Y(8.0),)) +@test name(dimz) == ("X", "Y") +@test shortname(dimz) == ("X", "Y") +@test units(dimz) == ("", "") +@test label(dimz) == ("X, Y") a = [1 2 3 4 2 3 4 5 @@ -169,6 +172,8 @@ a = [1 2 3 4 dimz = (Dim{:row}((10, 30)), Dim{:column}((-20, 10))) da = DimensionalArray(a, dimz) @test name(dimz) == ("Dim row", "Dim column") +@test shortname(dimz) == ("row", "column") +@test label(dimz) == ("Dim row, Dim column") @test da[Dim{:row}(2)] == [3, 4, 5, 6] @test da[Dim{:column}(4)] == [4, 6, 7] @test da[Dim{:column}(1), Dim{:row}(3)] == 4 @@ -218,7 +223,6 @@ da = DimensionalArray(a, dimz) @test var(da; dims=X()) == [2.0 2.0] @test var(da; dims=Y()) == [0.5 0.5]' @test dims(var(da; dims=Y())) == (X(LinRange(143.0, 145.0, 2)), Y(LinRange(-38.0, -38.0, 1))) - a = [1 2 3; 4 5 6] da = DimensionalArray(a, dimz) @test median(da; dims=Y()) == [2.0 5.0]' @@ -271,8 +275,7 @@ dsp = permutedims(da) @test dims(dsp) == reverse(dims(da)) da = DimensionalArray(ones(5, 2, 4), (Y(10:20), Time(10:11), X(1:4))) dsp = permutedims(da, [3, 1, 2]) -dsp = permutedims(da, (3, 1, 2)) -# Dim dispatch +# Dim dispatch arg possibilities dsp = permutedims(da, [X, Y, Time]) dsp = permutedims(da, (X, Y, Time)) dsp = permutedims(da, [X(), Y(), Time()]) @@ -416,11 +419,11 @@ println("Dims with UnitRange") @btime d3($g); a = rand(5, 4, 3); -dimz = (Y((1u"m", 5u"m")), X(1:4), Time(1:3)) -da = DimensionalArray(a, dimz) +da = DimensionalArray(a, (Y((1u"m", 5u"m")), X(1:4), Time(1:3))) +dimz = dims(da) if VERSION > v"1.1-" - println("eachslice: normal, numbers + rebuild, dims + rebuild") + println("\n\neachslice: normal, numbers + rebuild, dims + rebuild") @btime (() -> eachslice($a; dims=2))(); @btime (() -> eachslice($da; dims=2))(); @btime (() -> eachslice($da; dims=Y))(); @@ -431,7 +434,8 @@ if VERSION > v"1.1-" @test [slice for slice in eachslice(da; dims=1)] == [slice for slice in eachslice(da; dims=Y)] end -println("mean: normal, numbers + rebuild, dims + rebuild") + +println("\n\nmean: normal, numbers + rebuild, dims + rebuild") @btime mean($a; dims=2); @btime mean($da; dims=2); @btime mean($da; dims=X); @@ -442,4 +446,4 @@ println("permutedims: normal, numbers + rebuild, dims + rebuild") println("reverse: normal, numbers + rebuild, dims + rebuild") @btime reverse($a; dims=1) @btime reverse($da; dims=1) -@btime reverse($da; dims=Y()) +@btime reverse($da; dims=Y)