|
||||
File indexing completed on 2025-01-18 09:10:56
0001 // This file is part of the ACTS project. 0002 // 0003 // Copyright (C) 2016 CERN for the benefit of the ACTS project 0004 // 0005 // This Source Code Form is subject to the terms of the Mozilla Public 0006 // License, v. 2.0. If a copy of the MPL was not distributed with this 0007 // file, You can obtain one at https://mozilla.org/MPL/2.0/. 0008 0009 #pragma once 0010 0011 #include "Acts/Utilities/Helpers.hpp" 0012 0013 #include <algorithm> 0014 #include <array> 0015 #include <cassert> 0016 #include <cmath> 0017 #include <iomanip> 0018 #include <limits> 0019 #include <ostream> 0020 #include <sstream> 0021 0022 namespace Acts { 0023 0024 /// A constrained step class for the steppers. 0025 /// 0026 /// This class is symmetrical for forward and backward propagation. The sign of 0027 /// the propagation direction should not enter here but rather be applied the 0028 /// step is actually taken. 0029 /// 0030 /// As simple as this class looks it hides a few very important details: 0031 /// - Overstepping handling. The step size sign will flip if we happened to pass 0032 /// our target. 0033 /// - Convergence handling. Smaller and smaller step sizes have to be used in 0034 /// order to converge on a target. 0035 /// 0036 /// Because of the points mentioned above, the update function will always 0037 /// prefer negative step sizes. A side effect of this is that we will propagate 0038 /// in the opposite direction if the target is "behind us". 0039 /// 0040 /// The hierarchy is: 0041 /// - Overstepping resolution / backpropagation 0042 /// - Convergence 0043 /// - Step into the void with `std::numeric_limits<double>::max()` 0044 class ConstrainedStep { 0045 public: 0046 /// the types of constraints 0047 /// from navigator - this would be a navigation step 0048 /// from actor - this would be an actor condition 0049 /// from user - this is user given for what reason ever 0050 enum class Type : int { Navigator = 0, Actor = 1, User = 2 }; 0051 0052 constexpr ConstrainedStep() = default; 0053 0054 /// constructor 0055 /// @param v is the user given initial value 0056 constexpr explicit ConstrainedStep(double v) { setUser(v); } 0057 0058 /// set accuracy 0059 /// 0060 /// this will set only the accuracy, as this is the most 0061 /// exposed to the Propagator 0062 /// 0063 /// @param v is the new accuracy value 0064 constexpr void setAccuracy(double v) { 0065 assert(v > 0 && "ConstrainedStep accuracy must be > 0."); 0066 // set the accuracy value 0067 m_accuracy = v; 0068 } 0069 0070 /// set user 0071 /// 0072 /// @param v is the new user value 0073 constexpr void setUser(double v) { 0074 // TODO enable assert; see https://github.com/acts-project/acts/issues/2543 0075 // assert(v != 0 && "ConstrainedStep user must be != 0."); 0076 // set the user value 0077 setValue(Type::User, v); 0078 } 0079 0080 /// returns the min step size 0081 constexpr double value() const { 0082 double min = *std::min_element(m_values.begin(), m_values.end()); 0083 // accuracy is always positive and therefore handled separately 0084 double result = std::min(std::abs(min), m_accuracy); 0085 return std::signbit(min) ? -result : result; 0086 } 0087 0088 /// Access a specific value 0089 /// 0090 /// @param type is the requested parameter type 0091 constexpr double value(Type type) const { 0092 return m_values[toUnderlying(type)]; 0093 } 0094 0095 /// Access the accuracy value 0096 constexpr double accuracy() const { return m_accuracy; } 0097 0098 /// release a certain constraint value 0099 /// 0100 /// @param type is the constraint type to be released 0101 constexpr void release(Type type) { setValue(type, kNotSet); } 0102 0103 /// release accuracy 0104 constexpr void releaseAccuracy() { m_accuracy = kNotSet; } 0105 0106 /// Update the step size of a certain type 0107 /// 0108 /// Only navigation and target abortion step size 0109 /// updates may change the sign due to overstepping 0110 /// 0111 /// @param v is the new value to be updated 0112 /// @param type is the constraint type 0113 constexpr void update(double v, Type type) { 0114 // check the current value and set it if appropriate 0115 // this will also allow signed values due to overstepping 0116 if (std::abs(v) < std::abs(value(type))) { 0117 // TODO enable assert; see 0118 // https://github.com/acts-project/acts/issues/2543 0119 // assert(value != 0 && "ConstrainedStep user must be != 0."); 0120 setValue(type, v); 0121 } 0122 } 0123 0124 std::ostream& toStream(std::ostream& os) const { 0125 // Helper method to avoid unreadable screen output 0126 auto streamValue = [&](double v) { 0127 os << std::setw(5); 0128 if (std::abs(v) == kNotSet) { 0129 os << (v > 0 ? "+∞" : "-∞"); 0130 } else { 0131 os << v; 0132 } 0133 }; 0134 0135 os << "("; 0136 streamValue(m_accuracy); 0137 os << ", "; 0138 streamValue(value(Type::Navigator)); 0139 os << ", "; 0140 streamValue(value(Type::Actor)); 0141 os << ", "; 0142 streamValue(value(Type::User)); 0143 os << ")"; 0144 0145 return os; 0146 } 0147 0148 std::string toString() const { 0149 std::stringstream dstream; 0150 toStream(dstream); 0151 return dstream.str(); 0152 } 0153 0154 private: 0155 static constexpr auto kNotSet = std::numeric_limits<double>::max(); 0156 0157 /// the step size tuple 0158 std::array<double, 3> m_values = {kNotSet, kNotSet, kNotSet}; 0159 /// the accuracy value - this can vary up and down given a good step estimator 0160 double m_accuracy = kNotSet; 0161 0162 constexpr void setValue(Type type, double v) { 0163 m_values[toUnderlying(type)] = v; 0164 } 0165 }; 0166 0167 inline std::ostream& operator<<(std::ostream& os, const ConstrainedStep& step) { 0168 return step.toStream(os); 0169 } 0170 0171 } // namespace Acts
[ Source navigation ] | [ Diff markup ] | [ Identifier search ] | [ general search ] |
This page was automatically generated by the 2.3.7 LXR engine. The LXR team |