#include <iostream>

#include <typeinfo>

enum class Direction

{

L,

R

} ;

template < int Value >

struct repeat

{

static const int head = Value ;

typedef repeat < Value > tail ;

} ;

template < int Value, typename Next >

struct cons

{

static const int head = Value ;

typedef Next tail ;

} ;

template < Direction, typename Left, typename Right >

struct step { } ;

template < typename Left, typename Right >

struct step < Direction :: L , Left, Right >

{

typedef typename Left :: tail left ;

typedef typename cons < Left :: head , Right > right ;

} ;

template < typename Left, typename Right >

struct step < Direction :: R , Left, Right >

{

typedef cons < Right :: head , Left > left ;

typedef typename Right :: tail right ;

} ;

template < typename TuringMachine, typename Left, typename Right, typename State = typename TuringMachine :: initial_state >

struct turing_machine

{

typedef typename TuringMachine :: template transition_table < Right :: head , State > transition ;

typedef step < transition :: direction , Left, cons < transition :: symbol , typename Right :: tail >> step ;

typedef turing_machine < TuringMachine, typename step :: left , typename step :: right , typename transition :: state > next ;

typedef typename next :: final_left final_left ;

typedef typename next :: final_right final_right ;

} ;

template < typename TuringMachine, typename Left, typename Right >

struct turing_machine < TuringMachine, Left, Right, typename TuringMachine :: final_state >

{

typedef Left final_left ;

typedef Right final_right ;

} ;

struct busy_beaver

{

struct A { } ;

struct B { } ;

struct H { } ;

template < int Sym, typename State >

struct transition_table { } ;

template <>

struct transition_table < 0 , A >

{

static const int symbol = 1 ;

static const Direction direction = Direction :: R ;

typedef B state ;

} ;

template <>

struct transition_table < 0 , B >

{

static const int symbol = 1 ;

static const Direction direction = Direction :: L ;

typedef A state ;

} ;

template <>

struct transition_table < 1 , A >

{

static const int symbol = 1 ;

static const Direction direction = Direction :: L ;

typedef B state ;

} ;

template <>

struct transition_table < 1 , B >

{

static const int symbol = 1 ;

static const Direction direction = Direction :: R ;

typedef H state ;

} ;

typedef A initial_state ;

typedef H final_state ;

} ;

int main ( )

{

using namespace std ;

typedef turing_machine < busy_beaver, repeat < 0 > , repeat < 0 >> tm ;

cout << typeid ( tm :: next ) . name ( ) << endl ;

cout << typeid ( tm :: next :: next ) . name ( ) << endl ;

cout << typeid ( tm :: next :: next :: next ) . name ( ) << endl ;

cout << typeid ( tm :: next :: next :: next :: next ) . name ( ) << endl ;

cout << typeid ( tm :: next :: next :: next :: next :: next ) . name ( ) << endl ;

cout << typeid ( tm :: next :: next :: next :: next :: next :: next ) . name ( ) << endl ;

cout << endl ;

cout << typeid ( tm :: final_left ) . name ( ) << endl ;

cout << typeid ( tm :: final_right ) . name ( ) << endl ;