File indexing completed on 2026-04-17 07:59:02
0001
0002
0003
0004
0005
0006
0007
0008
0009 #pragma once
0010
0011 #include "Acts/Definitions/Algebra.hpp"
0012 #include "Acts/Definitions/Common.hpp"
0013 #include "Acts/Geometry/GeometryContext.hpp"
0014 #include "Acts/Geometry/Polyhedron.hpp"
0015 #include "Acts/Utilities/Enumerate.hpp"
0016 #include "Acts/Utilities/GridAccessHelpers.hpp"
0017 #include "Acts/Utilities/Helpers.hpp"
0018 #include "Acts/Utilities/IAxis.hpp"
0019 #include "Acts/Utilities/Logger.hpp"
0020
0021 #include <algorithm>
0022 #include <array>
0023 #include <set>
0024 #include <string>
0025 #include <vector>
0026
0027 namespace Acts {
0028
0029
0030
0031
0032
0033
0034
0035
0036
0037
0038
0039
0040 std::vector<std::size_t> binSequence(std::array<std::size_t, 2u> minMaxBins,
0041 std::size_t expand, std::size_t nBins,
0042 Acts::AxisBoundaryType type);
0043
0044
0045
0046
0047
0048
0049
0050
0051
0052
0053
0054
0055
0056 template <typename grid_type>
0057 std::set<typename grid_type::index_t> localIndices(
0058 const grid_type& grid,
0059 const std::vector<typename grid_type::point_t>& queries,
0060 const std::vector<std::size_t>& expansion = {}) {
0061
0062 std::set<typename grid_type::index_t> lIndices;
0063
0064 if (queries.empty()) {
0065 throw std::runtime_error("IndexedSurfaceGridFiller: no query point given.");
0066 }
0067
0068 if (!expansion.empty() && expansion.size() != grid_type::DIM) {
0069 throw std::runtime_error(
0070 "IndexedSurfaceGridFiller: wrong dimension of bin expansion given.");
0071 }
0072
0073
0074 std::array<Acts::AxisBoundaryType, grid_type::DIM> axisTypes{};
0075 std::array<std::size_t, grid_type::DIM> axisBins{};
0076
0077 for (auto [ia, a] : enumerate(grid.axes())) {
0078 axisTypes[ia] = a->getBoundaryType();
0079 axisBins[ia] = a->getNBins();
0080 }
0081
0082
0083 std::array<std::array<std::size_t, 2u>, grid_type::DIM> binRanges = {};
0084 for (auto& br : binRanges) {
0085 br[0u] = std::numeric_limits<std::size_t>::max();
0086 br[1u] = 0u;
0087 }
0088
0089 for (const auto& q : queries) {
0090 auto qbin = grid.localBinsFromPosition(q);
0091 for (std::size_t ib = 0; ib < grid_type::DIM; ++ib) {
0092 auto iqb = qbin[ib];
0093 binRanges[ib][0u] = std::min(iqb, binRanges[ib][0u]);
0094 binRanges[ib][1u] = std::max(iqb, binRanges[ib][1u]);
0095 }
0096 }
0097
0098 if constexpr (grid_type::DIM == 1u) {
0099
0100 std::size_t expand = expansion.empty() ? 0u : expansion[0u];
0101 auto localBins0 =
0102 binSequence(binRanges[0u], expand, axisBins[0u], axisTypes[0u]);
0103 for (auto l0 : localBins0) {
0104 typename grid_type::index_t b;
0105 b[0u] = l0;
0106 lIndices.insert(b);
0107 }
0108 }
0109
0110 if constexpr (grid_type::DIM == 2u) {
0111
0112 std::size_t expand = expansion.empty() ? 0u : expansion[0u];
0113 auto localBins0 =
0114 binSequence(binRanges[0u], expand, axisBins[0u], axisTypes[0u]);
0115 expand = expansion.empty() ? 0u : expansion[1u];
0116 auto localBins1 =
0117 binSequence(binRanges[1u], expand, axisBins[1u], axisTypes[1u]);
0118 for (auto l0 : localBins0) {
0119 for (auto l1 : localBins1) {
0120 typename grid_type::index_t b;
0121 b[0u] = l0;
0122 b[1u] = l1;
0123 lIndices.insert(b);
0124 }
0125 }
0126 }
0127 return lIndices;
0128 }
0129
0130
0131
0132
0133
0134
0135
0136
0137 template <typename local_bin>
0138 std::string outputIndices(const std::set<local_bin>& lbins) {
0139 std::string rString;
0140 for (auto [ilb, lb] : Acts::enumerate(lbins)) {
0141 if (ilb == 0) {
0142 rString = "bins: [";
0143 } else {
0144 rString += ", [";
0145 }
0146 for (auto [ib, b] : Acts::enumerate(lb)) {
0147 if (ib != 0u) {
0148 rString += ", ";
0149 }
0150 rString += std::to_string(b);
0151 }
0152 rString += "]";
0153 }
0154 return rString;
0155 }
0156
0157
0158 struct IndexGridFiller {
0159
0160 std::vector<std::size_t> binExpansion = {};
0161
0162
0163 std::unique_ptr<const Logger> oLogger =
0164 getDefaultLogger("IndexGridFiller", Logging::INFO);
0165
0166
0167
0168
0169
0170
0171
0172
0173
0174
0175
0176
0177
0178
0179
0180
0181
0182
0183
0184
0185 template <typename index_grid, typename indexed_objects,
0186 typename reference_generator>
0187 void fill(
0188 const GeometryContext& gctx, index_grid& iGrid,
0189 const indexed_objects& iObjects, const reference_generator& rGenerator,
0190 const typename index_grid::grid_type::value_type& aToAll = {}) const {
0191
0192 for (auto [io, o] : enumerate(iObjects)) {
0193
0194 if (rangeContainsValue(aToAll, io)) {
0195 continue;
0196 }
0197
0198 auto refs = rGenerator.references(gctx, *o);
0199 std::vector<typename index_grid::grid_type::point_t> gridQueries;
0200 gridQueries.reserve(refs.size());
0201 for (const auto& ref : refs) {
0202
0203 gridQueries.push_back(
0204 GridAccessHelpers::castPosition<decltype(iGrid.grid)>(
0205 iGrid.transform * ref, iGrid.casts));
0206 }
0207 ACTS_DEBUG(gridQueries.size() << " reference points generated.");
0208 auto lIndices = localIndices<decltype(iGrid.grid)>(
0209 iGrid.grid, gridQueries, binExpansion);
0210 ACTS_DEBUG(lIndices.size() << " indices assigned.");
0211 if (oLogger->level() <= Logging::VERBOSE) {
0212 ACTS_VERBOSE("- list of indices: " << outputIndices(lIndices));
0213 }
0214
0215 for (const auto& li : lIndices) {
0216 auto& bContent = iGrid.grid.atLocalBins(li);
0217 if (!rangeContainsValue(bContent, io)) {
0218 bContent.push_back(io);
0219 }
0220 }
0221 }
0222
0223
0224 if (!aToAll.empty()) {
0225 assignToAll(iGrid, aToAll);
0226 }
0227 }
0228
0229
0230
0231
0232
0233
0234 template <typename index_grid, typename indices>
0235 void assignToAll(index_grid& iGrid, const indices& idcs) const {
0236 for (std::size_t gi = 0; gi < iGrid.grid.size(true); ++gi) {
0237 auto& bContent = iGrid.grid.at(gi);
0238 for (const auto& io : idcs) {
0239 if (!rangeContainsValue(bContent, io)) {
0240 bContent.push_back(io);
0241 }
0242 }
0243 }
0244 }
0245
0246
0247
0248
0249 const Logger& logger() const { return (*oLogger); }
0250 };
0251
0252 }