1 /*============================================================================= 2 Copyright (c) 2001-2011 Hartmut Kaiser 3 http://spirit.sourceforge.net/ 4 5 Distributed under the Boost Software License, Version 1.0. (See accompanying 6 file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) 7 =============================================================================*/ 8 #include <boost/config/warning_disable.hpp> 9 10 //[customize_karma_counter_includes 11 #include <boost/spirit/include/karma.hpp> 12 #include <iostream> 13 #include <vector> 14 //] 15 16 /////////////////////////////////////////////////////////////////////////////// 17 //[customize_karma_counter_data 18 namespace client 19 { 20 struct counter 21 { 22 // expose the current value of the counter as our iterator 23 typedef int iterator; 24 25 // expose 'int' as the type of each generated element 26 typedef int type; 27 counterclient::counter28 counter(int max_count) 29 : counter_(0), max_count_(max_count) 30 {} 31 32 int counter_; 33 int max_count_; 34 }; 35 } 36 //] 37 38 //[customize_karma_counter_traits 39 // All specializations of attribute customization points have to be placed into 40 // the namespace boost::spirit::traits. 41 // 42 // Note that all templates below are specialized using the 'const' type. 43 // This is necessary as all attributes in Karma are 'const'. 44 namespace boost { namespace spirit { namespace traits 45 { 46 // The specialization of the template 'is_container<>' will tell the 47 // library to treat the type 'client::counter' as a container providing 48 // the items to generate output from. 49 template <> 50 struct is_container<client::counter const> 51 : mpl::true_ 52 {}; 53 54 // The specialization of the template 'container_iterator<>' will be 55 // invoked by the library to evaluate the iterator type to be used 56 // for iterating the data elements in the container. 57 template <> 58 struct container_iterator<client::counter const> 59 { 60 typedef client::counter::iterator type; 61 }; 62 63 // The specialization of the templates 'begin_container<>' and 64 // 'end_container<>' below will be used by the library to get the iterators 65 // pointing to the begin and the end of the data to generate output from. 66 // These specializations respectively return the initial and maximum 67 // counter values. 68 // 69 // The passed argument refers to the attribute instance passed to the list 70 // generator. 71 template <> 72 struct begin_container<client::counter const> 73 { 74 static client::counter::iterator callboost::spirit::traits::begin_container75 call(client::counter const& c) 76 { 77 return c.counter_; 78 } 79 }; 80 81 template <> 82 struct end_container<client::counter const> 83 { 84 static client::counter::iterator callboost::spirit::traits::end_container85 call(client::counter const& c) 86 { 87 return c.max_count_; 88 } 89 }; 90 }}} 91 //] 92 93 //[customize_karma_counter_iterator_traits 94 // All specializations of attribute customization points have to be placed into 95 // the namespace boost::spirit::traits. 96 namespace boost { namespace spirit { namespace traits 97 { 98 // The specialization of the template 'deref_iterator<>' will be used to 99 // dereference the iterator associated with our counter data structure. 100 // Since we expose the current value as the iterator we just return the 101 // current iterator as the return value. 102 template <> 103 struct deref_iterator<client::counter::iterator> 104 { 105 typedef client::counter::type type; 106 callboost::spirit::traits::deref_iterator107 static type call(client::counter::iterator const& it) 108 { 109 return it; 110 } 111 }; 112 }}} 113 //] 114 115 /////////////////////////////////////////////////////////////////////////////// 116 namespace karma = boost::spirit::karma; 117 main()118int main() 119 { 120 //[customize_karma_counter 121 // use the instance of a 'client::counter' instead of a STL vector 122 client::counter count(4); 123 std::cout << karma::format(karma::int_ % ", ", count) << std::endl; // prints: '0, 1, 2, 3' 124 //] 125 return 0; 126 } 127 128