diff --git a/src/chunks.jl b/src/chunks.jl index 75d14c6..fed9fab 100644 --- a/src/chunks.jl +++ b/src/chunks.jl @@ -20,6 +20,9 @@ function subsetchunks_fallback(chunks::ChunkVector, subsets) # This is a fallback method that should work for Regular and Irregular chunks. # Assuming the desired subset is sorted, we simply compute the chunk for every element # in subs and collect everything together again in either a Regular or IrregularChunk + if isempty(subsets) + return RegularChunks(1, 0, 0) + end rev = if issorted(subsets) false elseif issorted(subsets; rev=true) @@ -108,7 +111,7 @@ function subsetchunks(chunks::RegularChunks, subsets::AbstractUnitRange) chunks = RegularChunks(chunks.chunksize, newoffset, newsize) # In case the new chunk is trivial and has length 1, we shorten the chunk size if length(chunks) == 1 - chunks = RegularChunks(newsize, 0, newsize) + chunks = RegularChunks(max(newsize, 1), 0, newsize) end return chunks end @@ -176,6 +179,9 @@ Base.show(io::IO, chunks::IrregularChunks) = Base.print(io, "IrregularChunks($(chunks.offsets))") function subsetchunks(chunks::IrregularChunks, subsets::UnitRange) + if isempty(subsets) + return IrregularChunks([0]) + end c1 = findchunk(chunks, first(subsets)) c2 = findchunk(chunks, last(subsets)) newoffsets = chunks.offsets[c1:(c2+1)] @@ -253,7 +259,7 @@ end function chunktype_from_chunksizes(chunksizes::AbstractVector) if length(chunksizes) == 1 # only a single chunk is affected - return RegularChunks(chunksizes[1], 0, chunksizes[1]) + return RegularChunks(max(chunksizes[1], 1), 0, chunksizes[1]) elseif length(chunksizes) == 2 # Two affected chunks chunksize = max(chunksizes[1], chunksizes[2]) diff --git a/test/runtests.jl b/test/runtests.jl index 873f9ba..ff1d876 100644 --- a/test/runtests.jl +++ b/test/runtests.jl @@ -119,6 +119,9 @@ function test_view(a) @test trueparent(a)[2:3, 3:4] == [4 4; 4 4] @test getindex_count(a) == 2 @test setindex_count(a) == 2 + + v2 = view(a, 2:3, 2:4, Int[]) + @test size(eachchunk(v2)) == (1, 1, 0) end function test_reductions(af) @@ -204,10 +207,12 @@ end @test a1[3] == 9:10 @test length(a1) == 3 @test size(a1) == (3,) - v1 = subsetchunks(a1, 1:10) - v2 = subsetchunks(a1, 4:9) - @test v1 === a1 - @test v2 === RegularChunks(5, 0, 6) + @test subsetchunks(a1, 1:10) === a1 + @test subsetchunks(a1, 4:9) === RegularChunks(5, 0, 6) + @test subsetchunks(a1, Int[]) === RegularChunks(1, 0, 0) + @test subsetchunks(a1, 5:4) === RegularChunks(1, 0, 0) + @test subsetchunks(a1, 2:2:8) === RegularChunks(3, 2, 4) + @test subsetchunks(a1, 10:-2:1) === RegularChunks(3, 2, 5) a2 = RegularChunks(2, 0, 20) @test a2[1] == 1:2 @test a2[2] == 3:4 @@ -232,6 +237,10 @@ end @test_throws BoundsError b1[6] @test subsetchunks(b1, 1:15) == IrregularChunks(; chunksizes=[3, 3, 4, 3, 2]) @test subsetchunks(b1, 3:10) == IrregularChunks(; chunksizes=[1, 3, 4]) + @test subsetchunks(b1, Int[]) == IrregularChunks(; chunksizes=Int[]) + @test subsetchunks(b1, 5:4) == IrregularChunks(; chunksizes=Int[]) + @test subsetchunks(b1, 2:2:15) == IrregularChunks(; chunksizes=[1, 2, 2, 1, 1]) + @test subsetchunks(b1, 14:-2:1) == IrregularChunks(; chunksizes=[1, 1, 2, 2, 1]) gridc = GridChunks(a1, a2, b1) @test eltype(gridc) <: Tuple{UnitRange,UnitRange,UnitRange} @test gridc[1, 1, 1] == (1:3, 1:2, 1:3)