DGtal 1.4.0
Loading...
Searching...
No Matches
IteratorCirculatorTraits.h
1
17#pragma once
18
29#if defined(IteratorCirculatorTraits_RECURSES)
30#error Recursive header files inclusion detected in IteratorCirculatorTraits.h
31#else // defined(IteratorCirculatorTraits_RECURSES)
33#define IteratorCirculatorTraits_RECURSES
34
35#if !defined IteratorCirculatorTraits_h
37#define IteratorCirculatorTraits_h
38
40// Inclusions
41#include<iterator>
42#include<boost/iterator/iterator_categories.hpp>
43#include<boost/iterator/iterator_facade.hpp>
45
46namespace DGtal
47{
48
50// tag classes for type (either Iterator or Circulator)
51struct IteratorType {};
53
55// tag classes for traversal category (Foward, Bidirectional, RandomAccess)
56// valid for both iterator and circulator
60
62namespace detail
63{
64
66
75 template <typename IC>
77 {
78 typedef char yes[1];
79 typedef char no[2];
80
81 template <typename C>
82 static yes& test(typename C::Type*);
83
84 template <typename C>
85 static no& test(...);
86
87 BOOST_STATIC_CONSTANT(bool, value = sizeof(test<IC>(0)) == sizeof(yes));
88 };
89
91
98 //default (for iterator type)
99 template <typename IC, typename ICType>
101 {
102 BOOST_STATIC_CONSTANT(bool, value = false);
103 };
104
105 //specialization for circulator type
106 template <typename IC>
108 {
109 BOOST_STATIC_CONSTANT(bool, value = true);
110 };
111
113
125 //default (there is no nested type called 'Type')
126 template <typename IC, bool flagHasNestedTypeCalledType = false>
128 {
129 BOOST_STATIC_CONSTANT(bool, value = false);
130 };
131
132 //specialization if there is a nested type called 'Type'
133 template <typename IC>
134 struct IsCirculator<IC,true>
135 {
137 BOOST_STATIC_CONSTANT(bool, value = IsCirculatorHelper::value);
138 };
139
140} //namespace detail
141
143
150template <typename IC>
156
157namespace detail
158{
160
168 template<bool b = false>
173 template<>
175 {
177 };
178}//namespace detail
179
181
189template<typename IC>
194
195//NB. To add a third type of iterator (let's say 'ThirdType'),
196//you should add a meta function 'IsThird' (like 'IsCirculator')
197//and add a boolean template parameter in IteratorCirculatorTypeImpl
198//so that IteratorCirculatorTypeImpl can be specialized to define
199//the nested type 'Type' as 'ThirdType'.
200
202
211//default
212template <typename C>
214 typedef C Category;
215};
216
217//for STL iterators
218template <>
219struct ToDGtalCategory<std::forward_iterator_tag> {
221};
222
223template <>
224struct ToDGtalCategory<std::bidirectional_iterator_tag> {
226};
227
228template <>
229struct ToDGtalCategory<std::random_access_iterator_tag> {
231};
232
233//for boost traversal categories
234template <>
235struct ToDGtalCategory<boost::forward_traversal_tag> {
237};
238
239template <>
240struct ToDGtalCategory<boost::bidirectional_traversal_tag> {
242};
243
244template <>
245struct ToDGtalCategory<boost::random_access_traversal_tag> {
247};
248
249
250
251
252#if (((BOOST_VERSION /100000)==1) && ((BOOST_VERSION / 100 % 1000 )<57))
253 template <>
254 struct ToDGtalCategory<boost::detail::iterator_category_with_traversal<std::input_iterator_tag,boost::forward_traversal_tag> > {
256 };
257 template <>
258 struct ToDGtalCategory<boost::detail::iterator_category_with_traversal<std::input_iterator_tag,boost::bidirectional_traversal_tag> > {
259 typedef BidirectionalCategory Category;
260 };
261
262 template <>
263 struct ToDGtalCategory<boost::detail::iterator_category_with_traversal<std::input_iterator_tag,boost::random_access_traversal_tag> > {
264 typedef RandomAccessCategory Category;
265 };
266#else
267 template <>
268 struct ToDGtalCategory<boost::iterators::detail::iterator_category_with_traversal<std::input_iterator_tag,boost::forward_traversal_tag> > {
270 };
271 template <>
272 struct ToDGtalCategory<boost::iterators::detail::iterator_category_with_traversal<std::input_iterator_tag,boost::bidirectional_traversal_tag> > {
274 };
275
276 template <>
277 struct ToDGtalCategory<boost::iterators::detail::iterator_category_with_traversal<std::input_iterator_tag,boost::random_access_traversal_tag> > {
279 };
280#endif
281
282
284
293template <typename IC>
295
296 typedef typename IteratorCirculatorType<IC>::Type
298
299 typedef typename ToDGtalCategory
300 <typename boost::iterator_category<IC>::type>::Category
302
303 typedef typename IC::value_type Value;
304 typedef typename IC::difference_type Difference;
305 typedef typename IC::pointer Pointer;
306 typedef typename IC::reference Reference;
307
308};
309
310template <class T>
314 typedef T Value;
315 typedef ptrdiff_t Difference;
316 typedef T* Pointer;
317 typedef T& Reference;
318};
319
320template <class T>
322{
325 typedef T Value;
326 typedef ptrdiff_t Difference;
327 typedef T const* Pointer;
328 typedef T const& Reference;
329};
330
331} // namespace DGtal
332
333// //
335
336#endif // !defined IteratorCirculatorTraits_h
337
338#undef IteratorCirculatorTraits_RECURSES
339#endif // else defined(IteratorCirculatorTraits_RECURSES)
DGtal is the top-level namespace which contains all DGtal functions and types.
STL namespace.
Aim: Checks whether type IC is a circular or a classical iterator. Static value set to 'true' for a c...
BOOST_STATIC_CONSTANT(bool, value=IsCirculatorHelper::value)
detail::IsCirculator< IC, detail::HasNestedTypeType< IC >::value > IsCirculatorHelper
Aim: Provides nested types for both iterators and circulators: Type, Category, Value,...
ToDGtalCategory< typenameboost::iterator_category< IC >::type >::Category Category
IteratorCirculatorType< IC >::Type Type
Aim: Provides the type of IC as a nested type: either IteratorType or CirculatorType.
detail::IteratorCirculatorTypeImpl< IsCirculator< IC >::value >::Type Type
Aim: Provides the DGtal category matching C {ForwardCategory,BidirectionalCategory,...
Aim: Checks whether type IC has a nested type called 'Type' or not. NB: from en.wikipedia....
static yes & test(typename C::Type *)
BOOST_STATIC_CONSTANT(bool, value=sizeof(test< IC >(0))==sizeof(yes))
Aim: In order to check whether type IC is a circular or a classical iterator, the nested type called ...
BOOST_STATIC_CONSTANT(bool, value=false)
BOOST_STATIC_CONSTANT(bool, value=IsCirculatorHelper::value)
IsCirculatorFromType< IC, typename IC::Type > IsCirculatorHelper
Aim: Checks whether type IC is a circular or a classical iterator. Static value set to 'true' for a c...
BOOST_STATIC_CONSTANT(bool, value=false)
Aim: Defines the Iterator or Circulator type as a nested type according to the value of b.