File indexing completed on 2025-01-18 09:12:46
0001
0002
0003
0004
0005
0006
0007
0008
0009 #include <boost/test/data/test_case.hpp>
0010 #include <boost/test/unit_test.hpp>
0011
0012 #include "Acts/Definitions/Algebra.hpp"
0013 #include "Acts/Definitions/Units.hpp"
0014 #include "Acts/EventData/TrackParameters.hpp"
0015 #include "Acts/Geometry/GeometryContext.hpp"
0016 #include "Acts/MagneticField/ConstantBField.hpp"
0017 #include "Acts/MagneticField/MagneticFieldContext.hpp"
0018 #include "Acts/Propagator/ActorList.hpp"
0019 #include "Acts/Propagator/DirectNavigator.hpp"
0020 #include "Acts/Propagator/EigenStepper.hpp"
0021 #include "Acts/Propagator/MaterialInteractor.hpp"
0022 #include "Acts/Propagator/Navigator.hpp"
0023 #include "Acts/Propagator/Propagator.hpp"
0024 #include "Acts/Propagator/StandardAborters.hpp"
0025 #include "Acts/Propagator/SurfaceCollector.hpp"
0026 #include "Acts/Tests/CommonHelpers/CylindricalTrackingGeometry.hpp"
0027 #include "Acts/Tests/CommonHelpers/FloatComparisons.hpp"
0028
0029 #include <cmath>
0030 #include <iostream>
0031 #include <memory>
0032 #include <numbers>
0033 #include <random>
0034 #include <utility>
0035 #include <vector>
0036
0037 namespace Acts {
0038 class Surface;
0039 }
0040
0041 namespace bdata = boost::unit_test::data;
0042 using namespace Acts::UnitLiterals;
0043
0044 namespace Acts::Test {
0045
0046
0047 GeometryContext tgContext = GeometryContext();
0048 MagneticFieldContext mfContext = MagneticFieldContext();
0049
0050 CylindricalTrackingGeometry cGeometry(tgContext);
0051 auto tGeometry = cGeometry();
0052
0053
0054 Navigator navigator({tGeometry});
0055 DirectNavigator dnavigator;
0056
0057 using BField = ConstantBField;
0058 using Stepper = EigenStepper<>;
0059 using ReferencePropagator = Propagator<Stepper, Navigator>;
0060 using DirectPropagator = Propagator<Stepper, DirectNavigator>;
0061
0062 const double Bz = 2_T;
0063 auto bField = std::make_shared<BField>(Vector3{0, 0, Bz});
0064 Stepper estepper(bField);
0065 Stepper dstepper(bField);
0066
0067 ReferencePropagator rpropagator(std::move(estepper), std::move(navigator));
0068 DirectPropagator dpropagator(std::move(dstepper), std::move(dnavigator));
0069
0070 const int ntests = 1000;
0071 const int skip = 0;
0072 bool referenceTiming = false;
0073 bool oversteppingTest = false;
0074 double oversteppingMaxStepSize = 1_mm;
0075
0076
0077
0078
0079
0080
0081
0082
0083
0084
0085
0086
0087
0088
0089 template <typename rpropagator_t, typename dpropagator_t>
0090 void runTest(const rpropagator_t& rprop, const dpropagator_t& dprop, double pT,
0091 double phi, double theta, int charge, int index) {
0092 double dcharge = -1 + 2 * charge;
0093
0094 if (index < skip) {
0095 return;
0096 }
0097
0098
0099 double p = pT / sin(theta);
0100 CurvilinearTrackParameters start(Vector4(0, 0, 0, 0), phi, theta, dcharge / p,
0101 std::nullopt, ParticleHypothesis::pion());
0102
0103 using EndOfWorld = EndOfWorldReached;
0104
0105
0106 using ReferenceActorList =
0107 ActorList<MaterialInteractor, SurfaceCollector<>, EndOfWorld>;
0108
0109
0110 using Options = typename rpropagator_t::template Options<ReferenceActorList>;
0111 Options pOptions(tgContext, mfContext);
0112 if (oversteppingTest) {
0113 pOptions.stepping.maxStepSize = oversteppingMaxStepSize;
0114 }
0115
0116
0117 auto& sCollector = pOptions.actorList.template get<SurfaceCollector<>>();
0118 sCollector.selector.selectSensitive = true;
0119 sCollector.selector.selectMaterial = true;
0120
0121
0122 const auto& pResult = rprop.propagate(start, pOptions).value();
0123 auto& cSurfaces = pResult.template get<SurfaceCollector<>::result_type>();
0124 auto& cMaterial = pResult.template get<MaterialInteractor::result_type>();
0125 const Surface& destination = pResult.endParameters->referenceSurface();
0126
0127 std::cout << " - the standard navigator yielded "
0128 << cSurfaces.collected.size() << " collected surfaces" << std::endl;
0129
0130 if (!referenceTiming) {
0131
0132 std::vector<const Surface*> surfaceSequence;
0133 surfaceSequence.reserve(cSurfaces.collected.size());
0134 for (auto& cs : cSurfaces.collected) {
0135 surfaceSequence.push_back(cs.surface);
0136 }
0137
0138
0139 using DirectActorList = ActorList<MaterialInteractor, SurfaceCollector<>>;
0140
0141
0142 using DirectOptions =
0143 typename dpropagator_t::template Options<DirectActorList>;
0144 DirectOptions dOptions(tgContext, mfContext);
0145
0146 dOptions.navigation.surfaces = surfaceSequence;
0147
0148 auto& dCollector = dOptions.actorList.template get<SurfaceCollector<>>();
0149 dCollector.selector.selectSensitive = true;
0150 dCollector.selector.selectMaterial = true;
0151
0152
0153 const auto& ddResult =
0154 dprop.propagate(start, destination, dOptions).value();
0155 auto& ddSurfaces = ddResult.template get<SurfaceCollector<>::result_type>();
0156 auto& ddMaterial = ddResult.template get<MaterialInteractor::result_type>();
0157
0158
0159 BOOST_CHECK_EQUAL(cSurfaces.collected.size(), ddSurfaces.collected.size());
0160 CHECK_CLOSE_REL(cMaterial.materialInX0, ddMaterial.materialInX0, 1e-3);
0161
0162
0163 const auto& dwResult = dprop.propagate(start, dOptions).value();
0164 auto& dwSurfaces = dwResult.template get<SurfaceCollector<>::result_type>();
0165
0166
0167 BOOST_CHECK_EQUAL(cSurfaces.collected.size(), dwSurfaces.collected.size());
0168 }
0169 }
0170
0171
0172
0173 BOOST_DATA_TEST_CASE(
0174 test_direct_navigator,
0175 bdata::random((bdata::engine = std::mt19937(), bdata::seed = 20,
0176 bdata::distribution = std::uniform_real_distribution<double>(
0177 0.15_GeV, 10_GeV))) ^
0178 bdata::random(
0179 (bdata::engine = std::mt19937(), bdata::seed = 21,
0180 bdata::distribution = std::uniform_real_distribution<double>(
0181 -std::numbers::pi, std::numbers::pi))) ^
0182 bdata::random(
0183 (bdata::engine = std::mt19937(), bdata::seed = 22,
0184 bdata::distribution = std::uniform_real_distribution<double>(
0185 1., std::numbers::pi - 1.))) ^
0186 bdata::random((bdata::engine = std::mt19937(), bdata::seed = 23,
0187 bdata::distribution =
0188 std::uniform_int_distribution<std::uint8_t>(0, 1))) ^
0189 bdata::xrange(ntests),
0190 pT, phi, theta, charge, index) {
0191
0192 runTest(rpropagator, dpropagator, pT, phi, theta, charge, index);
0193 }
0194
0195 }