@@ -26,6 +26,8 @@ struct HistEdge{T,I}
26
26
end
27
27
HistEdge (edge:: AbstractRange ) = HistEdge (first (edge), last (edge), length (edge) - 1 )
28
28
29
+ Base. eltype (:: HistEdge{T} ) where {T} = T
30
+
29
31
30
32
function lookup (edge:: HistEdge{T,I} , x:: T ) where {T,I}
31
33
U = _unitless (T)
51
53
52
54
function _hist_inner! (:: HistogramBinning ,
53
55
dest:: AbstractArray{R,N} ,
54
- edges:: NTuple{N,HistEdge{T,I }} ,
55
- coord:: NTuple{N,T } ,
56
- weight:: U
57
- ) where {R, N, T, I, U }
56
+ edges:: Tuple{Vararg{HistEdge,N }} ,
57
+ coord:: Tuple{Vararg{Any,N} } ,
58
+ weight:: W
59
+ ) where {R, N, W }
58
60
idx = map (ii -> lookup (edges[ii], coord[ii])[1 ], ntuple (identity, Val (N)))
59
61
dest[idx... ] += oneunit (R) * weight
60
62
return nothing
64
66
65
67
function _hist_inner! (:: LinearBinning ,
66
68
dest:: AbstractArray{R,N} ,
67
- edges:: NTuple{N,HistEdge{T,I }} ,
68
- coord:: NTuple{N,T } ,
69
- weight:: U
70
- ) where {R, N, T, I, U }
69
+ edges:: Tuple{Vararg{HistEdge,N }} ,
70
+ coord:: Tuple{Vararg{Any,N} } ,
71
+ weight:: W
72
+ ) where {R, N, W }
71
73
Z = ntuple (identity, Val (N))
72
74
len = map (ii -> edges[ii]. nbin, Z)
73
75
idx = map (ii -> lookup (edges[ii], coord[ii])[1 ], Z)
74
76
# subtract off half of bin step to convert from fraction from left edge to fraction
75
77
# away from center
76
- del = map (ii -> lookup (edges[ii], coord[ii])[2 ] - one (U ) / 2 , Z)
78
+ del = map (ii -> lookup (edges[ii], coord[ii])[2 ] - one (W ) / 2 , Z)
77
79
78
80
# iterate through all corners of a bounding hypercube by counting counting through
79
81
# the permutations of {0,1} for each "axis" mapped to a bit in an integer
@@ -88,7 +90,7 @@ function _hist_inner!(::LinearBinning,
88
90
# the fraction of the weight to assign to a particular corner of the hypercube is
89
91
# the volume of the intersection between the bin and a similarly-shaped cube around
90
92
# the original coordinate
91
- frac = mapreduce (i -> bits[i] ? abs (del[i]) : one (U ) - abs (del[i]), * , Z)
93
+ frac = mapreduce (i -> bits[i] ? abs (del[i]) : one (del[i] ) - abs (del[i]), * , Z)
92
94
93
95
dest[idxs... ] += oneunit (R) * weight * frac
94
96
end
97
99
98
100
function _histogram! (binning:: B ,
99
101
dest:: AbstractArray{R,N} ,
100
- edges:: NTuple{N,HistEdge{T,I }} ,
101
- data:: AbstractVector{<:NTuple{N,T }} ,
102
+ edges:: Tuple{Vararg{HistEdge,N }} ,
103
+ data:: AbstractVector{<:Tuple{Vararg{Any,N} }} ,
102
104
weights:: Union{Nothing,<:AbstractVector} ,
103
- ) where {B<: AbstractBinning , R, N, T, I }
105
+ ) where {B<: AbstractBinning , R, N}
104
106
Z = ntuple (identity, Val (N))
105
107
106
108
# run through data vector and bin entries if they are within bounds
107
- wsum = isnothing (weights) ? zero (_unitless (T )) : zero (eltype (weights))
109
+ wsum = isnothing (weights) ? zero (_unitless (R )) : zero (eltype (weights))
108
110
for ii in eachindex (data)
109
111
coord = @inbounds data[ii]
110
112
if ! mapreduce (i -> edges[i]. lo ≤ coord[i] ≤ edges[i]. hi, & , Z)
111
113
continue
112
114
end
113
- w = isnothing (weights) ? one (_unitless (T )) : weights[ii]
115
+ w = isnothing (weights) ? one (_unitless (R )) : weights[ii]
114
116
_hist_inner! (binning, dest, edges, coord, w)
115
117
wsum += w
116
118
end
@@ -129,4 +131,8 @@ function _histogram!(binning::B,
129
131
return wsum
130
132
end
131
133
134
+ __hist_eltype (eltypes) = _invunit (typeof (mapreduce (oneunit, * , eltypes)))
135
+ _hist_eltype (edges:: Tuple{Vararg{AbstractRange}} ) = __hist_eltype (map (eltype, edges))
136
+ _hist_eltype (edges:: Tuple{Vararg{HistEdge}} ) = __hist_eltype (map (eltype, edges))
137
+
132
138
end # module Histogramming
0 commit comments