Integrator or solver of systems of ordinary differential equations. 
\( \vec u( 0 )  = \vec u_{ini} \).
The vector \( \vec u(t) \) can be represented using different types of containers, depending on the size and nature of the ODE system:
The method, which is supposed to be used by the solver, is represented by the template parameter Method.
    1#include <iostream>
    2#include <fstream>
    3#include <TNL/Containers/Vector.h>
    4#include <TNL/Algorithms/parallelFor.h>
    5#include <TNL/Containers/StaticVector.h>
    6#include <TNL/Solvers/ODE/ODESolver.h>
    7#include <TNL/Solvers/ODE/Methods/Euler.h>
    8
   13 
   14template< typename Device >
   15void
   16solveParallelODEs( const char* file_name )
   17{
   23
   25   const Real final_t = 50.0;
 
   26   const Real tau = 0.001;
 
   27   const Real output_time_step = 0.005;
 
   29
   31   const Real sigma_min( 10.0 ), rho_min( 15.0 ), beta_min( 1.0 );
 
   32   const int parametric_steps = 4;
   33   const Real sigma_step = 30.0 / ( parametric_steps - 1 );
 
   34   const Real rho_step = 21.0 / ( parametric_steps - 1 );
 
   35   const Real beta_step = 15.0 / ( parametric_steps - 1 );
 
   36   const int output_time_steps = 
ceil( final_t / output_time_step ) + 1;
 
   38
   40   const int results_size( output_time_steps * parametric_steps * parametric_steps * parametric_steps );
   42   auto results_view = results.getView();
   44
   48                                     const StaticVector& u,
   49                                     StaticVector& fu,
   53   {
   54      const Real& x = u[ 0 ];
 
   55      const Real& y = u[ 1 ];
 
   56      const Real& z = u[ 2 ];
 
   57      fu[ 0 ] = sigma_i * ( y - x );
   58      fu[ 1 ] = rho_j * x - y - x * z;
   59      fu[ 2 ] = -beta_k * z + x * y;
   60   };
   62
   65   {
   67      const Real sigma_i = sigma_min + idx[ 0 ] * sigma_step;
 
   68      const Real rho_j = rho_min + idx[ 1 ] * rho_step;
 
   69      const Real beta_k = beta_min + idx[ 2 ] * beta_step;
 
   71
   74      solver.setTau( tau );
   75      solver.setTime( 0.0 );
   76      StaticVector u( 1.0, 1.0, 1.0 );
   77      int time_step( 1 );
   78      results_view[ ( idx[ 0 ] * parametric_steps + idx[ 1 ] ) * parametric_steps + idx[ 2 ] ] = u;
   80
   82      while( time_step < output_time_steps ) {
   83         solver.setStopTime( 
TNL::min( solver.getTime() + output_time_step, final_t ) );
 
   85         solver.solve( u, f, sigma_i, rho_j, beta_k );
   87         const int k =
   88            ( ( time_step++ * parametric_steps + idx[ 0 ] ) * parametric_steps + idx[ 1 ] ) * parametric_steps + idx[ 2 ];
   89         results_view[ k ] = u;
   90      }
   92   };
   94
   96   const MultiIndex begin = { 0, 0, 0 };
   97   const MultiIndex end = { parametric_steps, parametric_steps, parametric_steps };
  100
  103   file.
open( file_name, std::ios::out );
 
  104   for( int sigma_idx = 0; sigma_idx < parametric_steps; sigma_idx++ )
  105      for( int rho_idx = 0; rho_idx < parametric_steps; rho_idx++ )
  106         for( int beta_idx = 0; beta_idx < parametric_steps; beta_idx++ ) {
  107            Real sigma = sigma_min + sigma_idx * sigma_step;
  108            Real rho = rho_min + rho_idx * rho_step;
  109            Real beta = beta_min + beta_idx * beta_step;
  110            file << 
"# sigma " << sigma << 
" rho " << rho << 
" beta " << beta << 
std::endl;
 
  111            for( int i = 0; i < output_time_steps - 1; i++ ) {
  112               int offset = ( ( i * parametric_steps + sigma_idx ) * parametric_steps + rho_idx ) * parametric_steps + beta_idx;
  113               auto u = results.getElement( offset );
  114               file << u[ 0 ] << 
" " << u[ 1 ] << 
" " << u[ 2 ] << 
std::endl;
 
  115            }
  117         }
  119}
  120 
  121int
  122main( int argc, char* argv[] )
  123{
  124   if( argc != 2 ) {
  126      return EXIT_FAILURE;
  127   }
  129   file_name += "/StaticODESolver-LorenzParallelExample-result.out";
  130 
  131   solveParallelODEs< TNL::Devices::Host >( file_name.getString() );
  132#ifdef __CUDACC__
  133   solveParallelODEs< TNL::Devices::Cuda >( file_name.getString() );
  134#endif
  135}
#define __cuda_callable__
Definition Macros.h:49
 
Array with constant size.
Definition StaticArray.h:21
 
Vector with constant size.
Definition StaticVector.h:19
 
Vector extends Array with algebraic operations.
Definition Vector.h:36
 
Class for managing strings.
Definition String.h:31
 
std::enable_if_t< std::is_integral_v< Begin > &&std::is_integral_v< End > > parallelFor(const Begin &begin, const End &end, typename Device::LaunchConfiguration launch_config, Function f, FunctionArgs... args)
Parallel for-loop function for 1D range specified with integral values.
Definition parallelFor.h:41
 
__cuda_callable__ auto ceil(const T &value) -> decltype(std::ceil(value))
This function returns the smallest integer value not less than the given value.
Definition Math.h:495
 
constexpr ResultType min(const T1 &a, const T2 &b)
This function returns minimum of two numbers.
Definition Math.h:24
 
First order Euler method.
Definition Euler.h:15
 
Integrator or solver of systems of ordinary differential equations.
Definition ODESolver.h:62
 
    1#include <iostream>
    2#include <TNL/Containers/Vector.h>
    3#include <TNL/Solvers/ODE/ODESolver.h>
    4#include <TNL/Solvers/ODE/Methods/Euler.h>
    5#include "write.h"
    6 
    8using Index = int;
    9 
   10template< typename Device >
   11void
   12solveHeatEquation( const char* file_name )
   13{
   16   using VectorView = typename Vector::ViewType;
   20 
   21
   22
   23
   25   const Real final_t = 0.05;
 
   26   const Real output_time_step = 0.005;
 
   27   const Index n = 41;
   28   const Real h = 1.0 / ( n - 1 );
 
   29   const Real tau = 0.1 * h * h;
 
   30   const Real h_sqr_inv = 1.0 / ( h * h );
 
   32 
   33
   34
   35
   37   Vector u( n );
   38   u.forAllElements(
   40      {
   42         if( x >= 0.4 && x <= 0.6 )
   43            value = 1.0;
   44         else
   45            value = 0.0;
   46      } );
   48   file.
open( file_name, std::ios::out );
 
   49   write( file, u, n, h, (
Real) 0.0 );
 
   51 
   52
   53
   54
   57   solver.setTau( tau );
   58   solver.setTime( 0.0 );
   60 
   61
   62
   63
   65   while( solver.getTime() < final_t ) {
   66      solver.setStopTime( 
TNL::min( solver.getTime() + output_time_step, final_t ) );
 
   68      auto f = [ = ] 
__cuda_callable__( Index i, 
const VectorView& u, VectorView& fu ) 
mutable 
   69      {
   70         if( i == 0 || i == n - 1 )  
   71            fu[ i ] = 0.0;
   72         else  
   73            fu[ i ] = h_sqr_inv * ( u[ i - 1 ] - 2.0 * u[ i ] + u[ i + 1 ] );
   74      };
   77      auto time_stepping = [ = ]( 
const Real& t, 
const Real& tau, 
const VectorView& u, VectorView& fu )
 
   78      {
   82      };
   84      solver.solve( u, time_stepping );
   85      write( file, u, n, h, solver.getTime() );  
   86   }
   88}
   89 
   90int
   91main( int argc, char* argv[] )
   92{
   93   if( argc != 2 ) {
   95      return EXIT_FAILURE;
   96   }
   98   file_name += "/ODESolver-HeatEquationExample-result.out";
   99 
  100   solveHeatEquation< TNL::Devices::Host >( file_name.getString() );
  101#ifdef __CUDACC__
  102   solveHeatEquation< TNL::Devices::Cuda >( file_name.getString() );
  103#endif
  104}