You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
enable field-order-agnostic overloads of fromarrow for struct types (#493)
Motivated by
beacon-biosignals/Legolas.jl#94 (comment)
Still requires:
- [x] docs
- [x] a test
- [x] a bit more due diligence benchmarking-wise. `@benchmark`ing the
access in the test case from
beacon-biosignals/Legolas.jl#94 didn't reveal
any perf difference, which seems like a good sign
---------
Co-authored-by: Eric Hanson <5846501+ericphanson@users.noreply.github.com>
Copy file name to clipboardExpand all lines: src/ArrowTypes/src/ArrowTypes.jl
+7-1Lines changed: 7 additions & 1 deletion
Original file line number
Diff line number
Diff line change
@@ -170,11 +170,15 @@ overload is necessary.
170
170
A few `ArrowKind`s have/allow slightly more custom overloads for their `fromarrow` methods:
171
171
* `ListKind{true}`: for `String` types, they may overload `fromarrow(::Type{T}, ptr::Ptr{UInt8}, len::Int) = ...` to avoid
172
172
materializing a `String`
173
-
* `StructKind`: must overload `fromarrow(::Type{T}, x...)` where individual fields are passed as separate
173
+
* `StructKind`:
174
+
* May overload `fromarrow(::Type{T}, x...)` where individual fields are passed as separate
174
175
positional arguments; so if my custom type `Interval` has two fields `first` and `last`, then I'd overload like
175
176
`ArrowTypes.fromarrow(::Type{Interval}, first, last) = ...`. Note the default implementation is
176
177
`ArrowTypes.fromarrow(::Type{T}, x...) = T(x...)`, so if your type already accepts all arguments in a constructor
177
178
no additional `fromarrow` method should be necessary (default struct constructors have this behavior).
179
+
* Alternatively, may overload `fromarrowstruct(::Type{T}, ::Val{fnames}, x...)`, where `fnames` is a tuple of the
180
+
field names corresponding to the values in `x`. This approach is useful when you need to implement deserialization
181
+
in a manner that is agnostic to the field order used by the serializer. When implemented, `fromarrowstruct` takes precedence over `fromarrow` in `StructKind` deserialization.
178
182
"""
179
183
function fromarrow end
180
184
fromarrow(::Type{T}, x::T) where {T} = x
@@ -302,6 +306,8 @@ struct StructKind <: ArrowKind end
Copy file name to clipboardExpand all lines: src/arraytypes/struct.jl
+22-15Lines changed: 22 additions & 15 deletions
Original file line number
Diff line number
Diff line change
@@ -19,7 +19,7 @@
19
19
20
20
An `ArrowVector` where each element is a "struct" of some kind with ordered, named fields, like a `NamedTuple{names, types}` or regular julia `struct`.
21
21
"""
22
-
struct Struct{T,S} <:ArrowVector{T}
22
+
struct Struct{T,S,fnames} <:ArrowVector{T}
23
23
validity::ValidityBitmap
24
24
data::S# Tuple of ArrowVector
25
25
ℓ::Int
@@ -33,23 +33,29 @@ isnamedtuple(T) = false
33
33
istuple(::Type{<:Tuple}) =true
34
34
istuple(T) =false
35
35
36
-
@propagate_inboundsfunction Base.getindex(s::Struct{T,S}, i::Integer) where {T,S}
0 commit comments