wibble 0.1.28
|
00001 00006 #include <iterator> 00007 00008 #include <wibble/amorph.h> 00009 #include <wibble/range.h> 00010 #include <wibble/cast.h> 00011 00012 #ifndef WIBBLE_CONSUMER_H 00013 #define WIBBLE_CONSUMER_H 00014 00015 namespace wibble { 00016 00017 template< typename T > struct Consumer; 00018 00019 template< typename T > 00020 struct ConsumerInterface 00021 { 00022 typedef T InputType; 00023 virtual void consume( const T &a ) = 0; 00024 virtual void consume( Range< T > s ) = 0; 00025 virtual ~ConsumerInterface() {} 00026 }; 00027 00028 template< typename T, typename W > 00029 struct ConsumerMorph : Morph< ConsumerMorph< T, W >, W, ConsumerInterface< T > > 00030 { 00031 ConsumerMorph() {} 00032 ConsumerMorph( const W &w ) : Morph< ConsumerMorph, W, ConsumerInterface< T > >( w ) {} 00033 00034 virtual void consume( const T &a ) { 00035 return this->wrapped().consume( a ); 00036 } 00037 00038 virtual void consume( Range< T > s ) { 00039 while ( !s.empty() ) { 00040 consume( s.head() ); 00041 s = s.tail(); 00042 } 00043 } 00044 }; 00045 00046 template< typename T, typename Self > 00047 struct ConsumerMixin : mixin::Comparable< Self > 00048 { 00049 Self &self() { return *static_cast< Self * >( this ); } 00050 const Self &self() const { return *static_cast< const Self * >( this ); } 00051 typedef std::output_iterator_tag iterator_category; 00052 typedef T ConsumedType; 00053 00054 bool operator<=( const Self &o ) const { return this <= &o; } 00055 Consumer< T > &operator++() { return self(); } 00056 Consumer< T > &operator++(int) { return self(); } 00057 Consumer< T > &operator*() { return self(); } 00058 Consumer< T > &operator=( const T &a ) { 00059 self()->consume( a ); 00060 return self(); 00061 } 00062 }; 00063 00064 template< typename T > 00065 struct Consumer: Amorph< Consumer< T >, ConsumerInterface< T > >, 00066 ConsumerMixin< T, Consumer< T > > 00067 { 00068 typedef Amorph< Consumer< T >, ConsumerInterface< T > > Super; 00069 00070 typedef void value_type; 00071 typedef void difference_type; 00072 typedef void pointer; 00073 typedef void reference; 00074 00075 Consumer( const MorphInterface< ConsumerInterface< T > > &i ) : Super( i ) {} 00076 Consumer() {} 00077 00078 void consume( const T &a ) { 00079 return this->implementation()->consume( a ); 00080 } 00081 00082 Consumer< T > &operator=( const T &a ) { 00083 consume( a ); 00084 return *this; 00085 } 00086 // output iterator - can't read or move 00087 }; 00088 00089 template< typename T, typename Out > 00090 struct ConsumerFromIterator : ConsumerMixin< T, ConsumerFromIterator< T, Out > > 00091 { 00092 ConsumerFromIterator( Out out ) : m_out( out ) {} 00093 void consume( const T& a ) { 00094 *(*m_out) = a; 00095 ++(*m_out); 00096 } 00097 protected: 00098 Out m_out; 00099 }; 00100 00101 template< typename R > 00102 Consumer< typename R::ConsumedType > consumerMorph( R r ) { 00103 return ConsumerMorph< typename R::ConsumedType , R >( r ); 00104 } 00105 00106 // insert iterators 00107 template< typename Out > 00108 Consumer< typename Out::container_type::value_type > consumer( Out out ) { 00109 return consumerMorph( 00110 ConsumerFromIterator< typename Out::container_type::value_type, Out >( out ) ); 00111 } 00112 00113 // containers 00114 template< typename T > 00115 typename IsType< Consumer< typename T::value_type >, typename T::iterator >::T consumer( T &c ) { 00116 return consumer( std::inserter( c, c.end() ) ); 00117 } 00118 00119 // consumers 00120 template< typename T > 00121 Consumer< T > consumer( const ConsumerInterface< T > &t ) { 00122 return t; 00123 } 00124 00125 } 00126 00127 #endif