diff options
Diffstat (limited to 'src/boost/libs/numeric/odeint/examples/heun.cpp')
-rw-r--r-- | src/boost/libs/numeric/odeint/examples/heun.cpp | 170 |
1 files changed, 170 insertions, 0 deletions
diff --git a/src/boost/libs/numeric/odeint/examples/heun.cpp b/src/boost/libs/numeric/odeint/examples/heun.cpp new file mode 100644 index 00000000..34fe12c4 --- /dev/null +++ b/src/boost/libs/numeric/odeint/examples/heun.cpp @@ -0,0 +1,170 @@ +/* + [auto_generated] + libs/numeric/odeint/examples/heun.cpp + + [begin_description] + Examplary implementation of the method of Heun. + [end_description] + + Copyright 2012 Karsten Ahnert + Copyright 2012 Mario Mulansky + + Distributed under the Boost Software License, Version 1.0. + (See accompanying file LICENSE_1_0.txt or + copy at http://www.boost.org/LICENSE_1_0.txt) + */ + +#include <iostream> + + +#include <boost/fusion/container/vector.hpp> +#include <boost/fusion/container/generation/make_vector.hpp> + +#include <boost/array.hpp> + +#include <boost/numeric/odeint.hpp> + + + + + + +namespace fusion = boost::fusion; + +//[ heun_define_coefficients +template< class Value = double > +struct heun_a1 : boost::array< Value , 1 > { + heun_a1( void ) + { + (*this)[0] = static_cast< Value >( 1 ) / static_cast< Value >( 3 ); + } +}; + +template< class Value = double > +struct heun_a2 : boost::array< Value , 2 > +{ + heun_a2( void ) + { + (*this)[0] = static_cast< Value >( 0 ); + (*this)[1] = static_cast< Value >( 2 ) / static_cast< Value >( 3 ); + } +}; + + +template< class Value = double > +struct heun_b : boost::array< Value , 3 > +{ + heun_b( void ) + { + (*this)[0] = static_cast<Value>( 1 ) / static_cast<Value>( 4 ); + (*this)[1] = static_cast<Value>( 0 ); + (*this)[2] = static_cast<Value>( 3 ) / static_cast<Value>( 4 ); + } +}; + +template< class Value = double > +struct heun_c : boost::array< Value , 3 > +{ + heun_c( void ) + { + (*this)[0] = static_cast< Value >( 0 ); + (*this)[1] = static_cast< Value >( 1 ) / static_cast< Value >( 3 ); + (*this)[2] = static_cast< Value >( 2 ) / static_cast< Value >( 3 ); + } +}; +//] + + +//[ heun_stepper_definition +template< + class State , + class Value = double , + class Deriv = State , + class Time = Value , + class Algebra = boost::numeric::odeint::range_algebra , + class Operations = boost::numeric::odeint::default_operations , + class Resizer = boost::numeric::odeint::initially_resizer +> +class heun : public +boost::numeric::odeint::explicit_generic_rk< 3 , 3 , State , Value , Deriv , Time , + Algebra , Operations , Resizer > +{ + +public: + + typedef boost::numeric::odeint::explicit_generic_rk< 3 , 3 , State , Value , Deriv , Time , + Algebra , Operations , Resizer > stepper_base_type; + + typedef typename stepper_base_type::state_type state_type; + typedef typename stepper_base_type::wrapped_state_type wrapped_state_type; + typedef typename stepper_base_type::value_type value_type; + typedef typename stepper_base_type::deriv_type deriv_type; + typedef typename stepper_base_type::wrapped_deriv_type wrapped_deriv_type; + typedef typename stepper_base_type::time_type time_type; + typedef typename stepper_base_type::algebra_type algebra_type; + typedef typename stepper_base_type::operations_type operations_type; + typedef typename stepper_base_type::resizer_type resizer_type; + typedef typename stepper_base_type::stepper_type stepper_type; + + heun( const algebra_type &algebra = algebra_type() ) + : stepper_base_type( + fusion::make_vector( + heun_a1<Value>() , + heun_a2<Value>() ) , + heun_b<Value>() , heun_c<Value>() , algebra ) + { } +}; +//] + + +const double sigma = 10.0; +const double R = 28.0; +const double b = 8.0 / 3.0; + +struct lorenz +{ + template< class State , class Deriv > + void operator()( const State &x_ , Deriv &dxdt_ , double t ) const + { + typename boost::range_iterator< const State >::type x = boost::begin( x_ ); + typename boost::range_iterator< Deriv >::type dxdt = boost::begin( dxdt_ ); + + dxdt[0] = sigma * ( x[1] - x[0] ); + dxdt[1] = R * x[0] - x[1] - x[0] * x[2]; + dxdt[2] = -b * x[2] + x[0] * x[1]; + } +}; + +struct streaming_observer +{ + std::ostream &m_out; + streaming_observer( std::ostream &out ) : m_out( out ) { } + template< typename State , typename Value > + void operator()( const State &x , Value t ) const + { + m_out << t; + for( size_t i=0 ; i<x.size() ; ++i ) m_out << "\t" << x[i]; + m_out << "\n"; + } +}; + + + +int main( int argc , char **argv ) +{ + using namespace std; + using namespace boost::numeric::odeint; + + + //[ heun_example + typedef boost::array< double , 3 > state_type; + heun< state_type > h; + state_type x = {{ 10.0 , 10.0 , 10.0 }}; + + integrate_const( h , lorenz() , x , 0.0 , 100.0 , 0.01 , + streaming_observer( std::cout ) ); + + //] + + return 0; +} |