DGtal  1.2.0
testIteratorFunctions.cpp
Go to the documentation of this file.
1 
31 #include <iostream>
32 #include <list>
33 #include <vector>
34 #include "DGtal/base/Common.h"
35 #include "DGtal/base/IteratorFunctions.h"
36 #include "DGtal/base/Circulator.h"
37 #include "DGtal/base/ReverseIterator.h"
39 
40 using namespace std;
41 using namespace DGtal;
42 
44 // Functions for testing class IteratorFunctions.
46 template<typename Container, typename T>
47 struct Tool
48 {
49  static void add(Container& c, const T& obj)
50  {
51  c.push_back(obj);
52  }
53 };
54 
55 #include <forward_list>
56 //specialization for forward lists
57 template<typename T>
58 struct Tool<std::forward_list<int>, T>
59 {
60  static void add(std::forward_list<int>& c, const T& obj)
61  {
62  c.push_front(obj);
63  }
64 };
65 
71 template<typename Container>
72 bool testAdvance(Container c)
73 {
74  unsigned int nbok = 0;
75  unsigned int nb = 0;
76 
77  trace.beginBlock ( "Advance..." );
78 
80  typedef typename Container::iterator I;
81  typedef typename IteratorCirculatorTraits<I>::Category Category;
82  trace.info() << typeid(Category()).name() << std::endl;
83 
90 
91  //classical iterator
92  I res = c.begin();
93  while ((nb+1) < 5)
94  {
95  ++res;
96  I i = c.begin();
97  DGtal::advanceIterator(i, (nb+1));
98  if ( (i != c.begin()) && ( i == res ) )
99  nbok++;
100  nb++;
101  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
102  }
103 
104  //circulator
105  Circulator<I> cres = Circulator<I>(c.begin(), c.begin(), c.end());
106  while ((nb+1) < 5)
107  {
108  ++cres;
109  Circulator<I> ci = Circulator<I>(c.begin(), c.begin(), c.end());
110  DGtal::advanceIterator(ci, (nb+1));
111  if ( (ci != Circulator<I>(c.begin(), c.begin(), c.end()))
112  && ( ci == cres ) )
113  nbok++;
114  nb++;
115  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
116  }
117 
118  trace.endBlock();
119 
120  return (nbok == nb);
121 }
122 
128 template<typename Container>
129 bool testSize(Container c)
130 {
131  unsigned int nbok = 0;
132  unsigned int nb = 0;
133 
134  trace.beginBlock ( "Size..." );
135 
137  typedef typename Container::iterator I;
138  typedef typename IteratorCirculatorTraits<I>::Category Category;
139  trace.info() << typeid(Category()).name() << std::endl;
140 
141  trace.info() << "empty underlying range" << std::endl;
142  if ( rangeSize(c.begin(), c.end()) == 0 )
143  nbok++;
144  nb++;
145  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
146  if ( rangeSize( Circulator<I>(c.begin(), c.begin(), c.end()),
147  Circulator<I>(c.end(), c.begin(), c.end()) ) == 0 )
148  nbok++;
149  nb++;
150  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
151  if ( subRangeSize(c.begin(), c.end()) == 0 )
152  nbok++;
153  nb++;
154  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
155  if ( subRangeSize( Circulator<I>(c.begin(), c.begin(), c.end()),
156  Circulator<I>(c.end(), c.begin(), c.end()) ) == 0 )
157  nbok++;
158  nb++;
159  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
160 
163 
164  trace.info() << "underlying range of one element" << std::endl;
165  if ( rangeSize(c.begin(), c.end()) == 1 )
166  nbok++;
167  nb++;
168  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
169  if ( rangeSize( Circulator<I>(c.begin(), c.begin(), c.end()),
170  Circulator<I>(c.begin(), c.begin(), c.end()) ) == 1 )
171  nbok++;
172  nb++;
173 
181 
182  trace.info() << "two equal iterators" << std::endl;
183  if ( rangeSize(c.begin(), c.begin()) == 0 )
184  nbok++;
185  nb++;
186  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
187  if ( subRangeSize(c.begin(), c.begin()) == 0 )
188  nbok++;
189  nb++;
190  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
191  if ( subRangeSize( Circulator<I>(c.begin(), c.begin(), c.end()),
192  Circulator<I>(c.begin(), c.begin(), c.end()) ) == 0 )
193  nbok++;
194  nb++;
195  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
196 
197 
198  trace.info() << "whole range (of 7 elements)" << std::endl;
199  if ( rangeSize(c.begin(), c.end()) == 7 )
200  nbok++;
201  nb++;
202  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
203  if ( rangeSize( Circulator<I>(c.begin(), c.begin(), c.end()),
204  Circulator<I>(c.begin(), c.begin(), c.end()) ) == 7 )
205  nbok++;
206  nb++;
207  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
208 
210  I itb = c.begin(); ++itb;
211  I ite = itb;
212  ite++; ite++; ite++; ite++;
213 
214  trace.info() << "subrange (of 4 elements)" << std::endl;
215  if ( rangeSize(itb, ite) == 4 )
216  nbok++;
217  nb++;
218  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
219  if ( rangeSize( Circulator<I>(itb, c.begin(), c.end()),
220  Circulator<I>(ite, c.begin(), c.end()) ) == 4 )
221  nbok++;
222  nb++;
223  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
224  if ( subRangeSize(itb, ite) == 4 )
225  nbok++;
226  nb++;
227  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
228  if ( subRangeSize( Circulator<I>(itb, c.begin(), c.end()),
229  Circulator<I>(ite, c.begin(), c.end()) ) == 4 )
230  nbok++;
231  nb++;
232  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
233 
234 
235  trace.endBlock();
236 
237  return (nbok == nb);
238 }
239 
240 
246 template<typename Container>
247 bool testMiddle(Container c)
248 {
249  unsigned int nbok = 0;
250  unsigned int nb = 0;
251 
252  trace.beginBlock ( "Middle iterator..." );
253 
255  typedef typename Container::iterator I;
256  typedef typename IteratorCirculatorTraits<I>::Category Category;
257  trace.info() << typeid(Category()).name() << std::endl;
258 
259  trace.info() << "empty underlying range" << std::endl;
260  if ( rangeMiddle(c.begin(), c.end()) == c.begin() )
261  nbok++;
262  nb++;
263  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
264  if ( rangeMiddle( Circulator<I>(c.begin(), c.begin(), c.end()),
265  Circulator<I>(c.begin(), c.begin(), c.end()) )
266  == Circulator<I>(c.begin(), c.begin(), c.end()) )
267  nbok++;
268  nb++;
269  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
270  if ( subRangeMiddle(c.begin(), c.end()) == c.begin() )
271  nbok++;
272  nb++;
273  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
274  if ( subRangeMiddle( Circulator<I>(c.begin(), c.begin(), c.end()),
275  Circulator<I>(c.end(), c.begin(), c.end()) )
276  == Circulator<I>(c.begin(), c.begin(), c.end()) )
277  nbok++;
278  nb++;
279  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
280 
283 
284  trace.info() << "underlying range of one element" << std::endl;
285  if ( rangeMiddle(c.begin(), c.end()) == c.begin() )
286  nbok++;
287  nb++;
288  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
289  if ( rangeMiddle( Circulator<I>(c.begin(), c.begin(), c.end()),
290  Circulator<I>(c.begin(), c.begin(), c.end()) )
291  == Circulator<I>(c.begin(), c.begin(), c.end()) )
292  nbok++;
293  nb++;
294  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
295 
304 
305  trace.info() << "two equal iterators" << std::endl;
306  if ( rangeMiddle(c.begin(), c.begin()) == c.begin() )
307  nbok++;
308  nb++;
309  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
310  if ( subRangeMiddle(c.begin(), c.begin()) == c.begin() )
311  nbok++;
312  nb++;
313  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
314  if ( subRangeMiddle( Circulator<I>(c.begin(), c.begin(), c.end()),
315  Circulator<I>(c.begin(), c.begin(), c.end()) )
316  == Circulator<I>(c.begin(), c.begin(), c.end()) )
317  nbok++;
318  nb++;
319  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
320 
322  I itb = c.begin();
323  I ite = itb;
324  ite++; ite++; ite++;
325  ite++; ite++; ite++; ite++;
326  I res1 = itb;
327  res1++; res1++; res1++;
328  I res2 = res1;
329  res1++;
330 
331  trace.info() << "whole range with odd number of elements" << std::endl;
332  if ( rangeMiddle(c.begin(), ite) == res2 )
333  nbok++;
334  nb++;
335  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
336  if ( rangeMiddle( Circulator<I>(c.begin(), c.begin(), ite),
337  Circulator<I>(c.begin(), c.begin(), ite) )
338  == Circulator<I>(res2, c.begin(), ite) )
339  nbok++;
340  nb++;
341  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
342 
343  trace.info() << "whole range with even number of elements" << std::endl;
344  if ( rangeMiddle(c.begin(), c.end()) == res1 )
345  nbok++;
346  nb++;
347  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
348  if ( rangeMiddle( Circulator<I>(c.begin(), c.begin(), c.end()),
349  Circulator<I>(c.begin(), c.begin(), c.end()) )
350  == Circulator<I>(res1, c.begin(), c.end()) )
351  nbok++;
352  nb++;
353  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
354 
356  ite = itb;
357  itb++;
358  ite++; ite++; ite++;
359  ite++; ite++; ite++;
360 
361  trace.info() << "subrange with odd number of elements" << std::endl;
362  if ( rangeMiddle(itb, ite) == res2 )
363  nbok++;
364  nb++;
365  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
366  if ( rangeMiddle( Circulator<I>(itb, c.begin(), c.end()),
367  Circulator<I>(ite, c.begin(), c.end()) )
368  == Circulator<I>(res2, c.begin(), c.end()) )
369  nbok++;
370  nb++;
371  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
372  if ( subRangeMiddle(itb, ite) == res2 )
373  nbok++;
374  nb++;
375  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
376  if ( subRangeMiddle( Circulator<I>(itb, c.begin(), c.end()),
377  Circulator<I>(ite, c.begin(), c.end()) )
378  == Circulator<I>(res2, c.begin(), c.end()) )
379  nbok++;
380  nb++;
381  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
382 
384  ite++;
385 
386  trace.info() << "subrange with even number of elements" << std::endl;
387  if ( rangeMiddle(itb, ite) == res1 )
388  nbok++;
389  nb++;
390  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
391  if ( rangeMiddle( Circulator<I>(itb, c.begin(), c.end()),
392  Circulator<I>(ite, c.begin(), c.end()) )
393  == Circulator<I>(res1, c.begin(), c.end()) )
394  nbok++;
395  nb++;
396  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
397  if ( subRangeMiddle(itb, ite) == res1 )
398  nbok++;
399  nb++;
400  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
401  if ( subRangeMiddle( Circulator<I>(itb, c.begin(), c.end()),
402  Circulator<I>(ite, c.begin(), c.end()) )
403  == Circulator<I>(res1, c.begin(), c.end()) )
404  nbok++;
405  nb++;
406  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
407 
408  trace.endBlock();
409 
410  return (nbok == nb);
411 }
412 
416 template<typename IC>
417 bool testIsNotEmpty(const IC& itb, const IC& ite, const bool& aFlagIsNotEmpty)
418 {
419  return (isNotEmpty(itb,ite) == aFlagIsNotEmpty );
420 }
421 
427 template<typename Container>
428 bool testRange(Container c)
429 {
430  unsigned int nbok = 0;
431  unsigned int nb = 0;
432 
433  trace.beginBlock ( "empty / not empty..." );
434 
436  typedef typename Container::iterator I;
437  typedef typename IteratorCirculatorTraits<I>::Category Category;
438  trace.info() << typeid(Category()).name() << std::endl;
439 
440  trace.info() << "empty underlying range" << std::endl;
441  if ( testIsNotEmpty(c.begin(), c.end(), false) )
442  nbok++;
443  nb++;
444  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
445  if ( testIsNotEmpty(Circulator<I>(c.begin(), c.begin(), c.end()),
446  Circulator<I>(c.begin(), c.begin(), c.end()), false) )
447  nbok++;
448  nb++;
449  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
450  if ( testIsNotEmpty(ReverseIterator<Circulator<I> >(Circulator<I>(c.begin(), c.begin(), c.end())),
451  ReverseIterator<Circulator<I> >(Circulator<I>(c.begin(), c.begin(), c.end())), false) )
452  nbok++;
453  nb++;
454  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
455 
458 
459  trace.info() << "underlying range of one element" << std::endl;
460  if ( testIsNotEmpty(c.begin(), c.end(), true) )
461  nbok++;
462  nb++;
463  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
464  if ( testIsNotEmpty(Circulator<I>(c.begin(), c.begin(), c.end()),
465  Circulator<I>(c.begin(), c.begin(), c.end()), true) )
466  nbok++;
467  nb++;
468  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
469  if ( testIsNotEmpty(ReverseIterator<Circulator<I> >(Circulator<I>(c.begin(), c.begin(), c.end())),
470  ReverseIterator<Circulator<I> >(Circulator<I>(c.begin(), c.begin(), c.end())), true) )
471  nbok++;
472  nb++;
473  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
474 
483 
484  trace.info() << "two equal iterators" << std::endl;
485  if ( testIsNotEmpty(c.begin(), c.begin(), false) )
486  nbok++;
487  nb++;
488  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
489  if ( testIsNotEmpty(Circulator<I>(c.begin(), c.begin(), c.end()),
490  Circulator<I>(c.begin(), c.begin(), c.end()), true) )
491  nbok++;
492  nb++;
493  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
494 
496  I itb = c.begin(); itb++;
497  I ite = itb;
498  ite++; ite++;
499  ite++; ite++;
500 
501  trace.info() << "whole range" << std::endl;
502  if ( testIsNotEmpty(c.begin(), c.end(), true) )
503  nbok++;
504  nb++;
505  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
506  if ( testIsNotEmpty(Circulator<I>(itb, c.begin(), c.end()),
507  Circulator<I>(itb, c.begin(), c.end()), true) )
508  nbok++;
509  nb++;
510  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
511  if ( testIsNotEmpty(ReverseIterator<Circulator<I> >(Circulator<I>(itb, c.begin(), c.end())),
512  ReverseIterator<Circulator<I> >(Circulator<I>(itb, c.begin(), c.end())), true) )
513  nbok++;
514  nb++;
515  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
516 
517 
518  trace.info() << "subrange" << std::endl;
519  if ( testIsNotEmpty(itb, ite, true) )
520  nbok++;
521  nb++;
522  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
523  if ( testIsNotEmpty(Circulator<I>(itb, c.begin(), c.end()),
524  Circulator<I>(ite, c.begin(), c.end()), true) )
525  nbok++;
526  nb++;
527  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
528  if ( testIsNotEmpty(ReverseIterator<Circulator<I> >(Circulator<I>(itb, c.begin(), c.end())),
529  ReverseIterator<Circulator<I> >(Circulator<I>(ite, c.begin(), c.end())), true) )
530  nbok++;
531  nb++;
532  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
533 
534 
535  trace.endBlock();
536 
537  return (nbok == nb);
538 }
539 
541 // Standard services - public :
542 
543 int main( int argc, char** argv )
544 {
545  trace.beginBlock ( "Testing class IteratorFunctions" );
546  trace.info() << "Args:";
547  for ( int i = 0; i < argc; ++i )
548  trace.info() << " " << argv[ i ];
549  trace.info() << endl;
550 
551  std::forward_list<int> fl;
552  std::list<int> bl;
553  std::vector<int> v;
554 
555  bool res =
556  testAdvance(fl) &&
557  testAdvance(bl) &&
558  testAdvance(v) &&
559  testMiddle(fl) &&
560  testMiddle(bl) &&
561  testMiddle(v) &&
562  testSize(fl) &&
563  testSize(bl) &&
564  testSize(v) &&
565  testRange(fl) &&
566  testRange(bl) &&
567  testRange(v);
568 
569  trace.emphase() << ( res ? "Passed." : "Error." ) << endl;
570  trace.endBlock();
571  return res ? 0 : 1;
572 }
573 // //
Aim: Provides an adapter for classical iterators that can iterate through the underlying data structu...
Definition: Circulator.h:86
This class adapts any bidirectional iterator so that operator++ calls operator-- and vice versa.
void beginBlock(const std::string &keyword="")
std::ostream & emphase()
std::ostream & info()
double endBlock()
DGtal is the top-level namespace which contains all DGtal functions and types.
IteratorCirculatorTraits< IC >::Difference rangeSize(const IC &itb, const IC &ite)
IteratorCirculatorTraits< IC >::Difference subRangeSize(const IC &itb, const IC &ite)
IC subRangeMiddle(const IC &itb, const IC &ite)
IC rangeMiddle(const IC &itb, const IC &ite)
Trace trace
Definition: Common.h:154
void advanceIterator(IC &ic, typename IteratorCirculatorTraits< IC >::Difference n)
ToDGtalCategory< typename boost::iterator_category< IC >::type >::Category Category
ch add(Point(102.2, 50.2))
bool testRange(Container c)
bool testAdvance(Container c)
int main(int argc, char **argv)
bool testIsNotEmpty(const IC &itb, const IC &ite, const bool &aFlagIsNotEmpty)
bool testMiddle(Container c)
bool testSize(Container c)