Skip to content

Commit 82d2577

Browse files
committed
Add method for collection of Features as StructArray-
1 parent c2119c4 commit 82d2577

File tree

1 file changed

+18
-28
lines changed

1 file changed

+18
-28
lines changed

src/metadata.jl

Lines changed: 18 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -8,36 +8,26 @@ Feature(x; kwargs...) = Feature(x, values(kwargs))
88
Base.getproperty(f::Feature, s::Symbol) = s == :data ? getfield(f, 1) : s == :rest ? getfield(f, 2) : getproperty(getfield(f, 2), s)
99
Base.propertynames(f::Feature) = (:data, propertynames(f.rest)...)
1010

11-
#todo better function names
12-
"""
13-
Put a collection(Array) of Features in a StructArray
14-
"""
15-
function s_coll(iter::Array)
16-
unnested_iter = Base.Generator(iter) do geom_meta
17-
geom = getfield(geom_meta, :data) # well, the public accessor for this
18-
metadata = getfield(geom_meta, :rest)
19-
(; geometry=geom, metadata...) # I think the GeometryBasics name for this field is `:position`
20-
end
21-
soa = fieldarrays(StructArray(unnested_iter))
22-
return Feature(soa.geometry; Base.tail(soa)...)
11+
getnamestypes(::Type{Feature{T, Names, Types}}) where {T, Names, Types} = (T, Names, Types)
12+
13+
function StructArrays.staticschema(::Type{F}) where {F<:Feature} #explicitly give the "schema" of the object to StructArrays
14+
T, names, types = getnamestypes(F)
15+
NamedTuple{(:data, names...), Base.tuple_type_cons(T, types)}
2316
end
2417

25-
function GeometryBasics.Feature(elements::AbstractVector{XX}; rest...) where {XX}
26-
isempty(rest) && return elements # no meta to add!
27-
n = length(elements)
28-
for (k, v) in rest
29-
if v isa AbstractVector
30-
mn = length(v)
31-
mn != n && error("Metadata array needs to have same length as data.
32-
Found $(n) data items, and $mn metadata items")
33-
else
34-
error("Metadata needs to be an array with the same length as data items. Found: $(typeof(v))")
35-
end
36-
end
37-
nt = values(rest)
38-
# get the first element to get the per element named tuple type
39-
ElementNT = typeof(map(first, nt))
40-
return StructArray((geometry = elements, nt...))
18+
function StructArrays.createinstance(::Type{F}, x, args...) where {F<:Feature} #generate an instance of Feature type
19+
T , names, types = getnamestypes(F)
20+
Feature(x, NamedTuple{names, types}(args))
21+
end
22+
23+
function structarray(iter)
24+
cols = Tables.columntable(iter)
25+
structarray(first(cols), Base.tail(cols))
26+
end
27+
28+
function structarray(data, rest::NamedTuple{names, types}) where {names, types}
29+
F = Feature{eltype(data), names, StructArrays.eltypes(types)}
30+
return StructArray{F}(; data=data, rest...)
4131
end
4232

4333
#=---------------------------------------------------------------------------------------------

0 commit comments

Comments
 (0)