Skip to content

Commit 6c8f5c4

Browse files
asinghvi17meggart
andauthored
Convert fill values correctly from negative to unsigned integers (#165)
* Convert fill values correctly from negative to unsigned integers Positive integers are unaffected by this change anyway. * Only reinterpret negative integers when decoding fill values to unsigned --------- Co-authored-by: Fabian Gans <[email protected]>
1 parent b52be51 commit 6c8f5c4

File tree

1 file changed

+8
-1
lines changed

1 file changed

+8
-1
lines changed

src/metadata.jl

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -222,6 +222,13 @@ Base.eltype(::Metadata{T}) where T = T
222222
fill_value_decoding(v::AbstractString, T::Type{<:Number}) = parse(T, v)
223223
fill_value_decoding(v::Nothing, ::Any) = v
224224
fill_value_decoding(v, T) = T(v)
225-
fill_value_decoding(v::Integer, T::Type{<: Unsigned}) = reinterpret(T, signed(T)(v))
226225
fill_value_decoding(v::Number, T::Type{String}) = v == 0 ? "" : T(UInt8[v])
227226
fill_value_decoding(v, ::Type{ASCIIChar}) = v == "" ? nothing : v
227+
# Sometimes when translating between CF (climate and forecast) convention data
228+
# and Zarr groups, fill values are left as "negative integers" to encode unsigned
229+
# integers. So, we have to convert to the signed type with the same number of bytes
230+
# as the unsigned integer, then reinterpret as unsigned. That's how a fill value
231+
# of -1 can have a realistic meaning with an unsigned dtype.
232+
# However, we have to apply this correction only if the integer is negative.
233+
# If it's positive, then the value might be out of range of the signed integer type.
234+
fill_value_decoding(v::Integer, T::Type{<: Unsigned}) = sign(v) < 0 ? reinterpret(T, signed(T)(v)) : T(v)

0 commit comments

Comments
 (0)