File indexing completed on 2025-01-18 09:42:53
0001
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012
0013
0014
0015
0016
0017
0018 #ifndef BOOST_NUMERIC_ODEINT_ITERATOR_DETAIL_N_STEP_ITERATOR_IMPL_HPP_DEFINED
0019 #define BOOST_NUMERIC_ODEINT_ITERATOR_DETAIL_N_STEP_ITERATOR_IMPL_HPP_DEFINED
0020
0021 #include <boost/numeric/odeint/iterator/detail/ode_iterator_base.hpp>
0022 #include <boost/numeric/odeint/util/unit_helper.hpp>
0023
0024
0025
0026 namespace boost {
0027 namespace numeric {
0028 namespace odeint {
0029
0030
0031 template< class Iterator , class Stepper , class System , class State , typename Tag , class StepperTag >
0032 class n_step_iterator_impl;
0033
0034
0035
0036
0037
0038
0039
0040
0041
0042
0043
0044
0045
0046
0047
0048
0049 template< class Iterator , class Stepper , class System , class State , typename Tag >
0050 class n_step_iterator_impl< Iterator , Stepper , System , State , Tag , stepper_tag >
0051 : public detail::ode_iterator_base< Iterator , Stepper , System , State , Tag >
0052 {
0053 private:
0054
0055 typedef Stepper stepper_type;
0056 typedef System system_type;
0057 typedef typename boost::numeric::odeint::unwrap_reference< stepper_type >::type unwrapped_stepper_type;
0058 typedef State state_type;
0059 typedef typename traits::time_type< stepper_type >::type time_type;
0060 typedef typename traits::value_type< stepper_type >::type ode_value_type;
0061 #ifndef DOXYGEN_SKIP
0062 typedef detail::ode_iterator_base< Iterator , Stepper , System , State , Tag > base_type;
0063 #endif
0064
0065 public:
0066
0067
0068
0069
0070
0071
0072
0073
0074
0075
0076
0077 n_step_iterator_impl( stepper_type stepper , system_type sys , state_type &s ,
0078 time_type t , time_type dt , size_t num_of_steps )
0079 : base_type( stepper , sys , t , dt ) , m_t_start( t ) , m_state( &s ) ,
0080 m_steps(num_of_steps) , m_step( 0 )
0081 { }
0082
0083
0084
0085
0086
0087
0088
0089
0090 n_step_iterator_impl( stepper_type stepper , system_type sys , state_type &s )
0091 : base_type( stepper , sys ) , m_state( &s ) { }
0092
0093 protected:
0094
0095 friend class boost::iterator_core_access;
0096
0097 void increment()
0098 {
0099 if( this->m_step < this->m_steps )
0100 {
0101 unwrapped_stepper_type &stepper = this->m_stepper;
0102 stepper.do_step( this->m_system , *this->m_state , this->m_t , this->m_dt );
0103
0104 this->m_step++;
0105 this->m_t = this->m_t_start + static_cast< typename unit_value_type<time_type>::type >(this->m_step)*this->m_dt;
0106 } else {
0107 this->m_at_end = true;
0108
0109 }
0110 }
0111
0112 public:
0113 const state_type& get_state() const
0114 {
0115 return *m_state;
0116 }
0117
0118
0119 private:
0120 time_type m_t_start;
0121 time_type m_t_end;
0122 state_type* m_state;
0123 size_t m_steps;
0124 size_t m_step;
0125
0126 };
0127
0128
0129
0130
0131
0132
0133
0134
0135
0136
0137
0138
0139
0140
0141
0142
0143
0144
0145 template< class Iterator , class Stepper , class System , class State , typename Tag >
0146 class n_step_iterator_impl< Iterator , Stepper , System , State , Tag , dense_output_stepper_tag >
0147 : public detail::ode_iterator_base< Iterator , Stepper , System , State , Tag >
0148 {
0149 private:
0150
0151 typedef Stepper stepper_type;
0152 typedef System system_type;
0153 typedef typename boost::numeric::odeint::unwrap_reference< stepper_type >::type unwrapped_stepper_type;
0154 typedef State state_type;
0155 typedef typename traits::time_type< stepper_type >::type time_type;
0156 typedef typename traits::value_type< stepper_type >::type ode_value_type;
0157 #ifndef DOXYGEN_SKIP
0158 typedef detail::ode_iterator_base< Iterator , Stepper , System , State , Tag > base_type;
0159 #endif
0160
0161 public:
0162
0163
0164
0165
0166
0167
0168
0169
0170
0171
0172
0173 n_step_iterator_impl( stepper_type stepper , system_type sys , state_type &s ,
0174 time_type t , time_type dt , size_t num_of_steps )
0175 : base_type( stepper , sys , t , dt ) , m_t_start( t ) , m_state( &s ) ,
0176 m_steps( num_of_steps ) , m_step( 0 )
0177 {
0178 unwrapped_stepper_type &st = this->m_stepper;
0179 st.initialize( * ( this->m_state ) , this->m_t , this->m_dt );
0180 }
0181
0182
0183
0184
0185
0186
0187
0188
0189 n_step_iterator_impl( stepper_type stepper , system_type sys , state_type &s )
0190 : base_type( stepper , sys ) , m_state( &s )
0191 {
0192 }
0193
0194
0195
0196 protected:
0197
0198 friend class boost::iterator_core_access;
0199
0200 void increment( void )
0201 {
0202 if( this->m_step < this->m_steps )
0203 {
0204 unwrapped_stepper_type &stepper = this->m_stepper;
0205
0206 this->m_step++;
0207 this->m_t = this->m_t_start + static_cast< typename unit_value_type<time_type>::type >(this->m_step)*this->m_dt;
0208 while( detail::less_with_sign( stepper.current_time() , this->m_t ,
0209 stepper.current_time_step() ) )
0210 {
0211 stepper.do_step( this->m_system );
0212 }
0213 stepper.calc_state( this->m_t , *( this->m_state ) );
0214 } else {
0215 this->m_at_end = true;
0216 }
0217 }
0218
0219 public:
0220 const state_type& get_state() const
0221 {
0222 return *m_state;
0223 }
0224
0225
0226 private:
0227 time_type m_t_start;
0228 time_type m_t_end;
0229 state_type* m_state;
0230 size_t m_steps;
0231 size_t m_step;
0232 };
0233
0234 }
0235 }
0236 }
0237
0238
0239 #endif