Extension: Matrix functions
#include "dg/matrix/matrix.h"
exp_runge_kutta.h
Go to the documentation of this file.
1#include "dg/algorithm.h"
2#include "matrixsqrt.h"
3#include "lanczos.h"
4#include "tableau.h"
5
6namespace dg {
7namespace mat {
8
49template<class ContainerType>
51{
53 using container_type = ContainerType;
55 ExponentialStep() = default;
63 ExponentialStep( const ContainerType& copyable): m_u(copyable)
64 { }
65 const ContainerType& copyable()const{ return m_u;}
78 template< class MatrixFunction>
80 const ContainerType& u0, value_type& t1, ContainerType& u1,
81 value_type dt)
82 {
83 ode( [dt](value_type x){
84 return (exp( dt*x));}, u0, m_u);
85 dg::blas1::copy( m_u, u1);
86 t1 = t0 + dt;
87 }
88 private:
89 ContainerType m_u;
90};
91
123template<class ContainerType>
125{
127 using container_type = ContainerType;
138 ContainerType& copyable): m_rk(tableau), m_k(m_rk.num_stages(),
139 copyable), m_tmp(copyable), m_u(copyable)
140 { }
141 const ContainerType& copyable()const{ return m_tmp;}
142
146 template< class ExplicitRHS, class MatrixFunction>
147 void step( const std::tuple<ExplicitRHS,MatrixFunction>& ode, value_type t0, const
148 ContainerType& u0, value_type& t1, ContainerType& u1, value_type
149 dt, ContainerType& delta)
150 {
151 step ( ode, t0, u0, t1, u1, dt, delta, true);
152 }
153
170 template< class ExplicitRHS, class MatrixFunction>
171 void step( const std::tuple<ExplicitRHS, MatrixFunction>& ode, value_type t0,
172 const ContainerType& u0, value_type& t1, ContainerType& u1,
173 value_type dt)
174 {
175 step ( ode, t0, u0, t1, u1, dt, m_tmp, false);
176 }
178 unsigned order() const {
179 return m_rk.order();
180 }
182 unsigned embedded_order() const {
183 return m_rk.embedded_order();
184 }
186 unsigned num_stages() const{
187 return m_rk.num_stages();
188 }
189
190 private:
191 template< class ExplicitRHS, class MatrixFunction>
192 void step( const std::tuple<ExplicitRHS, MatrixFunction>& ode, value_type t0, const ContainerType& u0, value_type& t1, ContainerType& u1, value_type dt, ContainerType& delta, bool compute_delta)
193 {
194 // There may be a formulation that saves on a few matrix function applications
195 unsigned s = m_rk.num_stages();
196 value_type tu = t0;
197 if( t0 != m_t1 )
198 {
199 std::get<0>(ode)(t0, u0, m_k[0]); //freshly compute k_0
200 //std::cout << "t0 "<<t0<<" u0 "<<u0<<" k0 "<<m_k[0]<<"\n";
201 }
202 for ( unsigned i=1; i<s; i++)
203 {
204 std::get<1>(ode)( [&](value_type x){
205 return (exp( m_rk.c(i)*dt*x));}, u0, m_u);
206 for( unsigned j=0; j<i; j++)
207 {
208 //std::cout << "a(i j) "<<i<<" "<<j<<"\n";
209 if ( m_rk.a(i,j)(0) != 0)
210 {
211 std::get<1>(ode)([&](value_type x){ return
212 m_rk.a(i,j)(dt*x);}, m_k[j], m_tmp);
213 dg::blas1::axpby( dt, m_tmp, 1., m_u);
214 }
215 }
216 tu = DG_FMA( dt,m_rk.c(i),t0); //l=0
217 std::get<0>(ode)( tu, m_u, m_k[i]);
218 }
219 //Now add everything up to get solution and error estimate
220 // can't use u1 cause u0 can alias u1
221 std::get<1>(ode)( [dt](value_type x){
222 return (exp( dt*x));}, u0, m_u);
223 //std::cout <<" exp ( dt A) u0 = "<< m_u<<"\n";
224 if( compute_delta)
226 for( unsigned i=0; i<s; i++)
227 {
228 //std::cout << "b(i) "<<i<<"\n";
229 if( m_rk.b(i)(0) != 0)
230 {
231 std::get<1>(ode)([&](value_type x){ return
232 m_rk.b(i)(dt*x);}, m_k[i], m_tmp);
233 //std::cout << "b_i ( h A) (k) = "<<m_tmp<<"\n";
234 dg::blas1::axpby( dt, m_tmp, 1., m_u);
235 }
236 if( compute_delta && m_rk.bt(i)(0) != 0)
237 {
238 std::get<1>(ode)([&](value_type x){ return
239 m_rk.bt(i)(dt*x);}, m_k[i], m_tmp);
240 dg::blas1::axpby( dt, m_tmp, 1., delta);
241 }
242 }
243 dg::blas1::copy( m_u, u1);
244 if( compute_delta)
245 dg::blas1::axpby( 1., u1, -1., delta);
246 //make sure (t1,u1) is the last call to f
247 m_t1 = t1 = t0 + dt;
248 std::get<0>(ode)( t1, u1, m_k[0]);
249 //std::cout << "t1 "<<t1<<" u1 "<<u0<<" k0 "<<m_k[0]<<"\n";
250 }
251 FunctionalButcherTableau<value_type> m_rk;
252 std::vector<ContainerType> m_k;
253 value_type m_t1 = 1e300;//remember the last timestep at which ERK is called
254 ContainerType m_tmp, m_u;
255
256};
257
258} //namespace matrix
259} //namespace dg
void copy(const ContainerTypeIn &source, ContainerTypeOut &target)
void axpby(get_value_type< ContainerType > alpha, const ContainerType1 &x, get_value_type< ContainerType > beta, ContainerType &y)
Operator< real_type > delta(unsigned n)
typename TensorTraits< std::decay_t< Vector > >::value_type get_value_type
Classes for Krylov space approximations of a Matrix-Vector product.
Convert identifiers to their corresponding dg::mat::FunctionalButcherTableau.
Definition: tableau.h:323
Exponential Runge-Kutta fixed-step time-integration for .
Definition: exp_runge_kutta.h:125
void step(const std::tuple< ExplicitRHS, MatrixFunction > &ode, value_type t0, const ContainerType &u0, value_type &t1, ContainerType &u1, value_type dt, ContainerType &delta)
Advance one step with error estimate.
Definition: exp_runge_kutta.h:147
const ContainerType & copyable() const
Definition: exp_runge_kutta.h:141
void step(const std::tuple< ExplicitRHS, MatrixFunction > &ode, value_type t0, const ContainerType &u0, value_type &t1, ContainerType &u1, value_type dt)
Advance one step ignoring error estimate and embedded method.
Definition: exp_runge_kutta.h:171
unsigned num_stages() const
number of stages of the method given by the current Butcher Tableau
Definition: exp_runge_kutta.h:186
ExponentialERKStep(ConvertsToFunctionalButcherTableau< value_type > tableau, const ContainerType &copyable)
Reserve internal workspace for the integration.
Definition: exp_runge_kutta.h:137
ContainerType container_type
the type of the vector class in use
Definition: exp_runge_kutta.h:127
get_value_type< ContainerType > value_type
the value type of the time variable (float or double)
Definition: exp_runge_kutta.h:126
unsigned order() const
global order of the method given by the current Butcher Tableau
Definition: exp_runge_kutta.h:178
unsigned embedded_order() const
global order of the embedding given by the current Butcher Tableau
Definition: exp_runge_kutta.h:182
Exponential one step time-integration for .
Definition: exp_runge_kutta.h:51
void step(MatrixFunction &ode, value_type t0, const ContainerType &u0, value_type &t1, ContainerType &u1, value_type dt)
Advance one step via , .
Definition: exp_runge_kutta.h:79
ExponentialStep(const ContainerType &copyable)
Reserve internal workspace for the integration.
Definition: exp_runge_kutta.h:63
get_value_type< ContainerType > value_type
the value type of the time variable (float or double)
Definition: exp_runge_kutta.h:52
const ContainerType & copyable() const
Definition: exp_runge_kutta.h:65
ExponentialStep()=default
no memory allocation
ContainerType container_type
Definition: exp_runge_kutta.h:53
unsigned num_stages() const
The number of stages s.
Definition: tableau.h:99
unsigned order() const
global order of accuracy for the method represented by b
Definition: tableau.h:103
real_type c(unsigned i) const
Read the c_i coefficients.
Definition: tableau.h:77
function_type bt(unsigned j) const
Read the embedded bt_j coefficients.
Definition: tableau.h:95
function_type a(unsigned i, unsigned j) const
Read the a_ij coefficients.
Definition: tableau.h:69
unsigned embedded_order() const
global order of accuracy for the embedded method represented by bt
Definition: tableau.h:107
function_type b(unsigned j) const
Read the b_j coefficients.
Definition: tableau.h:86
Computation of for self-adjoint positive definite .
Definition: matrixsqrt.h:138