C++ Template Metaprogramming
Solutions to the exercises throughout the book
Loading...
Searching...
No Matches
exercise-5-10.hpp
Go to the documentation of this file.
1// ===-- chapter-5/exercise-5-10.hpp ---------------------- -*- C++ -*- --=== //
9#ifndef EXERCISE_5_10
10#define EXERCISE_5_10
11
12#include "chapter-5-tree.hpp"
13
14#include <boost/static_assert.hpp>
15
16#include <boost/mpl/begin_end.hpp>
17#include <boost/mpl/deref.hpp>
18#include <boost/mpl/greater.hpp>
19#include <boost/mpl/iterator_tags.hpp>
20#include <boost/mpl/next_prior.hpp>
21
22#include <boost/type_traits/is_same.hpp>
23
24
68namespace exercise_5_10 {
69
72
78template <typename T>
80{
81 typedef T tree_root;
83 typedef boost::mpl::forward_iterator_tag category;
84};
85
98template <typename Cur, typename Parent, int VisitCount>
100{
101 typedef Cur current_tree;
102 typedef Parent parent_iterator;
103 static int const visit_count = VisitCount;
104
106};
107
110
111} // namespace exercise_5_10
112
113
114namespace boost {
115namespace mpl {
116
119
126template<>
127struct end_impl<exercise_5_10::inorder_view_tag>
128{
129 template <typename S>
131};
132
135template<>
136struct begin_impl<exercise_5_10::inorder_view_tag>
137{
139 template <typename Self, typename Parent>
140 struct apply_on_iterator :
141 exercise_5_10::inorder_view_iterator<Self, Parent, 1> { };
142
144 template <typename Cur, typename L, typename R, typename Parent>
145 struct apply_on_iterator<chapter5::tree<Cur, L, R>, Parent>
146 : apply_on_iterator<
147 L,
148 exercise_5_10::inorder_view_iterator<
149 chapter5::tree<Cur, L, R>, Parent, 1>
150 > { };
151
153 template <typename Parent>
154 struct apply_on_iterator< chapter5::tree<>, Parent >
155 : boost::mpl::end<
156 exercise_5_10::inorder_view< chapter5::tree<> > > { };
157
159 template <typename S>
160 struct apply
161 : apply_on_iterator<
162 typename S::tree_root,
163 exercise_5_10::inorder_view_iterator_end
164 > { };
165};
166
178template <typename Cur, typename Parent, int VisitCount>
179struct next< exercise_5_10::inorder_view_iterator<Cur, Parent, VisitCount> >
180 : boost::mpl::eval_if<
181 boost::is_same<exercise_5_10::inorder_view_iterator_end, Parent>,
182 exercise_5_10::inorder_view_iterator_end,
183 next<
184 exercise_5_10::inorder_view_iterator<
185 typename Parent::current_tree,
186 typename Parent::parent_iterator,
187 Parent::visit_count>
188 >
189 > { };
191template <typename Cur, typename Parent>
192struct next< exercise_5_10::inorder_view_iterator<Cur, Parent, 0> >
193 : exercise_5_10::inorder_view_iterator<Cur, Parent, 1> { };
194
196template <typename Cur, typename L, typename R, typename Parent, int VisitCount>
197struct next< exercise_5_10::inorder_view_iterator<
198 chapter5::tree<Cur, L, R>, Parent, VisitCount> > { };
199
201template <typename Cur, typename L, typename R, typename Parent>
202struct next< exercise_5_10::inorder_view_iterator<
203 chapter5::tree<Cur, L, R>, Parent, 0> >
204 : next<
205 exercise_5_10::inorder_view_iterator<
206 L,
207 exercise_5_10::inorder_view_iterator<
208 chapter5::tree<Cur, L, R>, Parent, 1>,
209 0
210 >
211 > { };
213template <typename Cur, typename R, typename Parent>
214struct next< exercise_5_10::inorder_view_iterator<
215 chapter5::tree<Cur, void_, R>, Parent, 0> >
216 : next< exercise_5_10::inorder_view_iterator<
217 chapter5::tree<Cur, void_, R>, Parent, 1> > { };
219template <typename Cur, typename L, typename R, typename Parent>
220struct next< exercise_5_10::inorder_view_iterator<
221 chapter5::tree<Cur, L, R>, Parent, 1> >
223 chapter5::tree<Cur, L, R>, Parent, 2> { };
225template <typename Cur, typename L, typename R, typename Parent>
226struct next< exercise_5_10::inorder_view_iterator<
227 chapter5::tree<Cur, L, R>, Parent, 2> >
228 : next<
229 exercise_5_10::inorder_view_iterator<
230 R,
231 exercise_5_10::inorder_view_iterator<
232 chapter5::tree<Cur, L, R>, Parent, 3>,
233 0
234 >
235 > { };
237template <typename Cur, typename L, typename Parent>
238struct next< exercise_5_10::inorder_view_iterator<
239 chapter5::tree<Cur, L, void_>, Parent, 2> >
240 : next< exercise_5_10::inorder_view_iterator<
241 chapter5::tree<Cur, L, void_>, Parent, 3> > { };
244template <typename Cur, typename L, typename R, typename Parent>
245struct next< exercise_5_10::inorder_view_iterator<
246 chapter5::tree<Cur, L, R>, Parent, 3> >
247 : boost::mpl::eval_if<
248 boost::is_same<exercise_5_10::inorder_view_iterator_end, Parent>,
249 exercise_5_10::inorder_view_iterator_end,
250 next<
251 exercise_5_10::inorder_view_iterator<
252 typename Parent::current_tree,
253 typename Parent::parent_iterator,
254 Parent::visit_count>
255 >
256 > { };
257
260template <typename Cur, typename Parent, int VisitCount>
261struct deref< exercise_5_10::inorder_view_iterator<Cur, Parent, VisitCount> >
262{
263 typedef Cur type;
264};
265
267template <typename Cur, typename L, typename R, typename Parent, int VisitCount>
268struct deref< exercise_5_10::inorder_view_iterator<
269 chapter5::tree<Cur, L, R>, Parent, VisitCount> >
270{
271 typedef Cur type;
272};
273
275
276} // namespace mpl
277} // namespace boost
278
279#if 0
280
281template <typename T>
282struct preorder_view
283{
284
285};
286
287template <typename T>
288struct postorder_view
289{
290
291};
292
293#endif
294
295#endif // EXERCISE_5_10
Define a binary tree structure for future exercises.
Exists to inject functionality into the Boost MPL namespace.
Exists to inject functionality into the Boost namespace.
Provide utilities availble to all Chapter 5 solutions.
Encapsulate solution for Exercise 5-10.
inorder_view_iterator< void_, void_, 0 > inorder_view_iterator_end
Establish an end to the sequence.
Establish an iterator to contain in-order traversal of the binary tree.
inorder_view_iterator< Cur, Parent, VisitCount > type
A tag for tag-dispatched sequence metafunctions.
Compels iterators to traverse the tree "in order".
boost::mpl::forward_iterator_tag category