@@ -123,3 +123,44 @@ function compute_truncerr!(values::AbstractVector, ind)
123123 values[ind] .= zero(eltype(values))
124124 return norm(values)
125125end
126+
127+ function compute_truncerr(values:: AbstractVector{<:Number} , ind:: AbstractUnitRange )
128+ init = abs2(zero(eltype(values)))
129+ return sqrt(
130+ sum(abs2, view(values, firstindex(values): (first(ind) - 1 )); init) +
131+ sum(abs2, view(values, (last(ind) + 1 ): lastindex(values)); init)
132+ )
133+ end
134+
135+ function compute_truncerr(values:: AbstractVector{<:Number} , ind:: AbstractVector{Bool} )
136+ init = abs2(zero(eltype(values)))
137+ @inbounds for i in eachindex(values, ind)
138+ init += abs2(values[i] * ~ (ind[i]))
139+ end
140+ return sqrt(init)
141+ end
142+
143+ function compute_truncerr(values:: AbstractVector{<:Number} , ind:: AbstractVector{<:Integer} )
144+ sort!(ind)
145+ allind = eachindex(IndexLinear(), values)
146+ next_i, next_j = iterate(allind), iterate(ind)
147+ init = abs2(zero(eltype(values)))
148+
149+ while ! (isnothing(next_i) || isnothing(next_j))
150+ (i, state_i), (j, state_j) = (next_i, next_j)
151+ (i < j) && (@inbounds init += abs2(values[i]))
152+ (i <= j) && (next_i = iterate(allind, state_i))
153+ (j <= i) && (next_j = iterate(ind, state_j))
154+ end
155+
156+ while ! isnothing(next_i) # next_j is nothing
157+ (i, state_i) = next_i
158+ @inbounds init += abs2(values[i])
159+ next_i = iterate(allind, state_i)
160+ end
161+
162+ return sqrt(init)
163+ end
164+
165+ # generic fallback: no allocations but inaccurate
166+ compute_truncerr(values:: AbstractVector , ind) = sqrt(norm(values)^ 2 - norm(view(values, ind))^ 2 )
0 commit comments