SpECTRE Documentation Coverage Report
Current view: top level - ControlSystem - TimescaleTuner.hpp Hit Total Coverage
Commit: 697db44127ce57424c079f629b3283267ec6bd78 Lines: 6 50 12.0 %
Date: 2024-06-21 21:13:41
Legend: Lines: hit not hit

          Line data    Source code
       1           0 : // Distributed under the MIT License.
       2             : // See LICENSE.txt for details.
       3             : 
       4             : #pragma once
       5             : 
       6             : #include <array>
       7             : #include <cstddef>
       8             : #include <limits>
       9             : #include <optional>
      10             : #include <utility>
      11             : #include <variant>
      12             : 
      13             : #include "DataStructures/DataVector.hpp"
      14             : #include "Options/String.hpp"
      15             : 
      16             : /// \cond
      17             : namespace PUP {
      18             : class er;
      19             : }
      20             : /// \endcond
      21             : 
      22             : /*!
      23             :  * \ingroup ControlSystemGroup
      24             :  * \brief Manages control system timescales
      25             :  *
      26             :  * The TimescaleTuner adjusts the damping timescale, \f$\tau\f$, of the control
      27             :  * system.\n The damping timescale is restricted to
      28             :  * `min_timescale`\f$\le\tau\le\f$`max_timescale`
      29             :  *
      30             :  * The damping time is adjusted according to the following criteria:
      31             :  *
      32             :  * **Decrease** the timescale by a factor of `decrease_factor` if either \n
      33             :  * - the error is too large: \f$|Q| >\f$ `decrease_timescale_threshold`
      34             :  * OR
      35             :  * the error is changing quickly: \f$|\dot{Q}|\tau >\f$
      36             :  * `decrease_timescale_threshold`,\n
      37             :  * AND \n
      38             :  * - the error is growing: \f$\dot{Q}Q > 0\f$
      39             :  * OR
      40             :  * the expected change in \f$Q\f$ is less than half its current value:
      41             :  * \f$|\dot{Q}|\tau < |Q|/2\f$
      42             :  *
      43             :  * **Increase** the timescale by a factor of `increase_factor` if \n
      44             :  * - the error is sufficiently small: \f$|Q|<\f$ `increase_timescale_threshold`
      45             :  * \n
      46             :  * AND \n
      47             :  * - the expected change in \f$Q\f$ is less than the threshold:
      48             :  * \f$|\dot{Q}|\tau < \f$ `increase_timescale_threshold`
      49             :  *
      50             :  * If the template bool \p AllowDecrease is false, then the check for decreasing
      51             :  * the timescale will be ignored. This can be used if something else will be
      52             :  * controlling the decrease of the timescale.
      53             :  */
      54             : template <bool AllowDecrease>
      55           1 : class TimescaleTuner {
      56             :  public:
      57           0 :   static constexpr Options::String help{
      58             :       "TimescaleTuner: stores and dynamically updates the timescales for each "
      59             :       "component of a particular control system."};
      60           0 :   struct InitialTimescales {
      61           0 :     using type = std::variant<double, std::vector<double>>;
      62           0 :     static constexpr Options::String help = {
      63             :         "Initial timescales for each function of time. Can either be a single "
      64             :         "value which will be used for all components of a function of time, or "
      65             :         "a vector of values. The vector must have the same number of "
      66             :         "components as the function of time."};
      67             :   };
      68             : 
      69           0 :   struct MinTimescale {
      70           0 :     using type = double;
      71           0 :     static constexpr Options::String help = {"Minimum timescale"};
      72             :   };
      73             : 
      74           0 :   struct MaxTimescale {
      75           0 :     using type = double;
      76           0 :     static constexpr Options::String help = {"Maximum timescale"};
      77             :   };
      78             : 
      79           0 :   struct DecreaseThreshold {
      80           0 :     using type = double;
      81           0 :     static constexpr Options::String help = {
      82             :         "Threshold for decrease of timescale"};
      83             :   };
      84           0 :   struct IncreaseThreshold {
      85           0 :     using type = double;
      86           0 :     static constexpr Options::String help = {
      87             :         "Threshold for increase of timescale"};
      88             :   };
      89           0 :   struct IncreaseFactor {
      90           0 :     using type = double;
      91           0 :     static constexpr Options::String help = {"Factor to increase timescale"};
      92             :   };
      93           0 :   struct DecreaseFactor {
      94           0 :     using type = double;
      95           0 :     static constexpr Options::String help = {"Factor to decrease timescale"};
      96             :   };
      97             : 
      98           0 :   using options = tmpl::append<
      99             :       tmpl::list<InitialTimescales, MaxTimescale, MinTimescale,
     100             :                  IncreaseThreshold, IncreaseFactor>,
     101             :       tmpl::conditional_t<AllowDecrease,
     102             :                           tmpl::list<DecreaseThreshold, DecreaseFactor>,
     103             :                           tmpl::list<>>>;
     104             : 
     105           0 :   TimescaleTuner(
     106             :       const typename InitialTimescales::type& initial_timescale,
     107             :       double max_timescale, double min_timescale,
     108             :       double increase_timescale_threshold, double increase_factor,
     109             :       double decrease_timescale_threshold = std::numeric_limits<double>::max(),
     110             :       double decrease_factor = 1.0);
     111             : 
     112           0 :   TimescaleTuner() = default;
     113           0 :   TimescaleTuner(TimescaleTuner&&) = default;
     114           0 :   TimescaleTuner& operator=(TimescaleTuner&&) = default;
     115           0 :   TimescaleTuner(const TimescaleTuner&) = default;
     116           0 :   TimescaleTuner& operator=(const TimescaleTuner&) = default;
     117           0 :   ~TimescaleTuner() = default;
     118             : 
     119             :   /// Returns the current timescale for each component of a FunctionOfTime
     120           1 :   const DataVector& current_timescale() const;
     121             :   /// Manually sets all timescales to a specified value, unless the value is
     122             :   /// outside of the specified minimum and maximum timescale bounds, in which
     123             :   /// case it is set to the nearest bounded value.
     124           1 :   void set_timescale_if_in_allowable_range(double suggested_timescale);
     125             :   /// The update function responsible for modifying the timescale based on
     126             :   /// the control system errors
     127           1 :   void update_timescale(const std::array<DataVector, 2>& q_and_dtq);
     128             : 
     129             :   /// Return whether the timescales have been set
     130           1 :   bool timescales_have_been_set() const { return timescales_have_been_set_; }
     131             : 
     132             :   /// \brief Destructively resize the DataVector of timescales. All previous
     133             :   /// timescale information will be lost.
     134             :   /// \param num_timescales Number of components to resize to. Can be larger or
     135             :   /// smaller than the previous size. Must be greater than 0.
     136             :   /// \param fill_value Optional of what value to use to fill the new
     137             :   /// timescales. `std::nullopt` signifies to use the minimum of the initial
     138             :   /// timescales. Default is `std::nullopt`.
     139           1 :   void resize_timescales(
     140             :       size_t num_timescales,
     141             :       const std::optional<double>& fill_value = std::nullopt);
     142             : 
     143           0 :   void pup(PUP::er& p);
     144             : 
     145             :   template <bool LocalAllowDecrease>
     146           0 :   friend bool operator==(const TimescaleTuner<LocalAllowDecrease>& lhs,
     147             :                          const TimescaleTuner<LocalAllowDecrease>& rhs);
     148             : 
     149             :  private:
     150           0 :   void check_if_timescales_have_been_set() const;
     151             : 
     152           0 :   DataVector timescale_;
     153           0 :   bool timescales_have_been_set_{false};
     154           0 :   double initial_timescale_{std::numeric_limits<double>::signaling_NaN()};
     155           0 :   double max_timescale_;
     156           0 :   double min_timescale_;
     157           0 :   double decrease_timescale_threshold_;
     158           0 :   double increase_timescale_threshold_;
     159           0 :   double increase_factor_;
     160           0 :   double decrease_factor_;
     161             : };
     162             : 
     163             : template <bool AllowDecrease>
     164           0 : bool operator!=(const TimescaleTuner<AllowDecrease>& lhs,
     165             :                 const TimescaleTuner<AllowDecrease>& rhs);

Generated by: LCOV version 1.14