DGtal  0.9.2
testArithmeticalDSS.cpp
1
30 #include <iostream>
32 #include "DGtal/base/Common.h"
33 #include "DGtal/kernel/CPointPredicate.h"
34 #include "DGtal/base/CConstBidirectionalRange.h"
35 #include "DGtal/geometry/curves/ArithmeticalDSS.h"
36 #include "DGtal/geometry/curves/ArithmeticalDSSFactory.h"
37 #include "DGtal/geometry/curves/StabbingLineComputer.h"
39
40 using namespace std;
41 using namespace DGtal;
42
44 // Functions for testing class ArithmeticalDSS.
46
51 template <typename DSS>
52 bool mainTest()
53 {
54  BOOST_CONCEPT_ASSERT(( concepts::CPointPredicate<DSS> ));
55  BOOST_CONCEPT_ASSERT(( concepts::CConstBidirectionalRange<DSS> ));
56
57  typedef typename DSS::Point Point;
58
59  unsigned int nbok = 0;
60  unsigned int nb = 0;
61
62  trace.beginBlock ( "Main operators..." );
63
64  //operateur constructeur, copie, affectation
65  trace.info() << "constructor, copy, assignement, equality" << std::endl;
66
67  DSS dss(0, 1,
68  Point(0,0), Point(1,0),
69  Point(0,0), Point(1,0),
70  Point(0,0), Point(1,0) );
71  DSS dss2 = dss;
72  DSS dss3(Point(0,0), Point(1,1), true);
73  DSS dss4 = dss3;
74  dss3 = dss2 = dss;
75
76  //egalite, difference
77  DSS dss5(0, -1,
78  Point(1,0), Point(0,0),
79  Point(1,0), Point(0,0),
80  Point(1,0), Point(0,0) );
81
82  if ( (dss == dss2)
83  &&(dss == dss3)
84  &&(dss != dss4)
85  &&(dss == dss5) )
86  nbok++;
87  nb++;
88  trace.info() << "(" << nbok << "/" << nb << ") "
89  << std::endl;
90
91  //validite
92  trace.info() << "valid dss" << std::endl;
93  if ( dss.isValid() && dss3.isValid() && dss5.isValid() )
94  nbok++;
95  nb++;
96  trace.info() << "(" << nbok << "/" << nb << ") "
97  << std::endl;
98
99  DSS dss6(0, 1,
100  Point(1,0), Point(0,0),
101  Point(1,0), Point(0,0),
102  Point(1,0), Point(0,0) );
103
104  trace.info() << "not valid dss" << std::endl;
105  if (!dss6.isValid())
106  nbok++;
107  nb++;
108
109  trace.info() << "(" << nbok << "/" << nb << ") "
110  << std::endl;
111
112  //accessors
113  trace.info() << "a,b,mu,omega accessors" << std::endl;
114
115  if ( (dss.a() == 0)&&(dss.b() == 1)&&(dss.mu() == 0)&&(dss.omega() == 1) )
116  nbok++;
117  nb++;
118
119  trace.info() << "(" << nbok << "/" << nb << ") "
120  << std::endl;
121
122  trace.info() << "points accessors" << std::endl;
123  if ( (dss.front() == Point(1,0))&&(dss.back() == Point(0,0)) )
124  nbok++;
125  nb++;
126  if ( (dss.Ul() == Point(1,0))&&(dss.Uf() == Point(0,0)) )
127  nbok++;
128  nb++;
129  if ( (dss.Ll() == Point(1,0))&&(dss.Lf() == Point(0,0)) )
130  nbok++;
131  nb++;
132
133  trace.info() << "(" << nbok << "/" << nb << ") "
134  << std::endl;
135
136  DSS dss7(Point(0,0), Point(8,5), true);
137
138  trace.info() << "remainder, position, tests" << std::endl;
139  trace.info() << dss7 << std::endl;
140
141  if ( (dss7.isValid())
142  && (dss7.remainder( Point(8,5) ) == 0)
143  &&(dss7.remainder( Point(16,10) ) == 0)
144  &&(dss7.remainder( Point(3,2) ) == -1)
145  &&(dss7.remainder( Point(5,3) ) == 1) )
146  nbok++;
147  nb++;
148
149  trace.info() << "(" << nbok << "/" << nb << ") "
150  << std::endl;
151
152  if ( (dss7.orthogonalPosition( Point(0,0) ) == 0)
153  &&(dss7.orthogonalPosition( Point(8,5) ) == 89)
154  &&(dss7.orthogonalPosition( Point(1,0) ) == 8)
155  &&(dss7.orthogonalPosition( Point(-1,0) ) == -8) )
156  nbok++;
157  nb++;
158
159  trace.info() << "(" << nbok << "/" << nb << ") "
160  << std::endl;
161
162  if ( (dss7.isInDSL( Point(0,0) ))
163  &&(dss7.isInDSL( Point(16,10) ))
164  &&(dss7.isInDSL( Point(5,3) ))
165  &&(!dss7.isInDSL( Point(3,2) )) )
166  nbok++;
167  nb++;
168
169  trace.info() << "(" << nbok << "/" << nb << ") "
170  << std::endl;
171
172  if ( (dss7( Point(0,0) ))
173  &&(!dss7( Point(16,10) ))
174  &&(dss7( Point(5,3) ))
175  &&(!dss7( Point(3,2) ))
176  &&(!dss7( Point(-1,0) )) )
177  nbok++;
178  nb++;
179
180  trace.info() << "(" << nbok << "/" << nb << ") "
181  << std::endl;
182
183  trace.info() << "shift" << std::endl;
184  if (dss.remainder(dss.shift()) == dss.omega())
185  nbok++;
186  nb++;
187  trace.info() << "(" << nbok << "/" << nb << ") "
188  << std::endl;
189
190  trace.endBlock();
191
192  return nbok == nb;
193 }
194
195
197
203 template <typename DSS>
204 bool rangeTest(const DSS& dss)
205 {
206  unsigned int nbok = 0;
207  unsigned int nb = 0;
208
209  trace.beginBlock ( "Range/Iterator services..." );
210  trace.info() << dss << std::endl;
211
212  if (dss.isValid())
213  nbok++;
214  nb++;
215
216  trace.info() << "(" << nbok << "/" << nb << ") "
217  << std::endl;
218
219  {//forward pass
220  typedef typename DSS::ConstIterator I;
222  BOOST_CONCEPT_ASSERT(( boost_concepts::BidirectionalTraversalConcept<I> ));
223  bool res = true;
224  int c = 0;
225  for (I it = dss.begin(), itEnd = dss.end();
226  ( (it != itEnd)&&(res)&&(c<100) );
227  ++it, ++c)
228  {
229  trace.info() << *it << " ";
230  if ( !dss(*it) )
231  res = false;
232  }
233  trace.info() << " : " << c << " points " << std::endl;
234  trace.info() << std::endl;
235
236  if ( (res)&&(c == (dss.omega()+1))
237  &&(*dss.begin() == dss.back())
238  &&(*--dss.end() == dss.front()) )
239  nbok++;
240  nb++;
241
242  trace.info() << "(" << nbok << "/" << nb << ") "
243  << std::endl;
244  }
245
246  {//backward pass
247  typedef typename DSS::ConstReverseIterator I;
248  bool res = true;
249  int c = 0;
250  for (I it = dss.rbegin(), itEnd = dss.rend();
251  ( (it != itEnd)&&(res)&&(c<100) );
252  ++it, ++c)
253  {
254  trace.info() << *it << " ";
255  if ( !dss(*it) )
256  res = false;
257  }
258  trace.info() << " : " << c << " points " << std::endl;
259  trace.info() << std::endl;
260
261  if ( (res)&&(c == (dss.omega()+1))
262  &&(*dss.rbegin() == dss.front())
263  &&(*--dss.rend() == dss.back()) )
264  nbok++;
265  nb++;
266
267  trace.info() << "(" << nbok << "/" << nb << ") "
268  << std::endl;
269  }
270
271  trace.endBlock();
272
273  return nbok == nb;
274 }
275
277
288 template <typename DSS>
289 void extensionTest(const DSS& dss,
290  typename DSS::Point newPointToFront,
291  typename DSS::Point newPointToBack,
292  unsigned int& nbok, unsigned int& nb,
293  const unsigned short int& code = 0)
294 {
295  trace.info() << dss << std::endl;
296  if (dss.isValid())
297  nbok++;
298  nb++;
299  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
300
301  trace.info() << "to front " << newPointToFront << std::endl;
302  if (dss.isExtendableFront( newPointToFront ) == code)
303  nbok++;
304  nb++;
305  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
306
307  DSS mdss = dss; //local and modifiable copy
308  if (code == 0)
309  {
310  if ( (!mdss.extendFront(newPointToFront)) )
311  nbok++;
312  nb++;
313  }
314  else
315  {
316  if ( (mdss.extendFront(newPointToFront))&&(mdss.isValid()) )
317  nbok++;
318  nb++;
319  std::cerr << mdss.isValid() << std::endl;
320  }
321  trace.info() << mdss << std::endl;
322  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
323
324  trace.info() << "to back " << newPointToBack << std::endl;
325  if (dss.isExtendableBack( newPointToBack ) == code)
326  nbok++;
327  nb++;
328  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
329
330  mdss = dss; //local and modifiable copy
331  if (code == 0)
332  {
333  if ( (!mdss.extendBack(newPointToBack)) )
334  nbok++;
335  nb++;
336  }
337  else
338  {
339  if ( (mdss.extendBack(newPointToBack))&&(mdss.isValid()) )
340  nbok++;
341  nb++;
342  std::cerr << mdss.isValid() << std::endl;
343  }
344  trace.info() << mdss << std::endl;
345  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
346 }
347
349
359 template <typename DSS>
360 void retractionTest(const DSS& dss,
361  unsigned int& nbok,
362  unsigned int& nb,
363  bool res = true)
364 {
365  typedef typename DSS::Point Point;
366
367  trace.info() << dss << std::endl;
368  if (dss.isValid())
369  nbok++;
370  nb++;
371  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
372
373  //local and modifiable copy
374  DSS mdss = dss;
375
376  //forward test
377  Point first = mdss.back();
378  trace.info() << "remove " << first << std::endl;
379  if ( ( (mdss.retractBack())
380  && (mdss.isValid())
381  && (mdss(first) == false) ) == res )
382  nbok++;
383  nb++;
384  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
385
386  if (res)
387  {
388  if ( (mdss.extendBack(first))
389  && (mdss.isValid()) && (mdss == dss) )
390  nbok++;
391  nb++;
392  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
393  }
394
395  //backward test
396  Point last = mdss.front();
397  trace.info() << "remove " << last << std::endl;
398  if ( ( (mdss.retractFront())
399  && (mdss.isValid())
400  && (mdss(last) == false) ) == res )
401  nbok++;
402  nb++;
403  trace.info() << mdss << std::endl;
404  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
405
406  if (res)
407  {
408  if ( (mdss.extendFront(last))
409  && (mdss.isValid()) && (mdss == dss) )
410  nbok++;
411  nb++;
412  trace.info() << "(" << nbok << "/" << nb << ") " << std::endl;
413  }
414
415 }
416
422 template <typename DSS>
423 bool updateTest()
424 {
425  typedef typename DSS::Point Point;
426  typedef typename DSS::Vector Vector;
427
428  unsigned int nbok = 0;
429  unsigned int nb = 0;
430
431  trace.beginBlock ( "Extension services..." );
432
433  if (nbok == nb)
434  {
435  trace.info() << "not connected point" << std::endl;
436  DSS dss(Point(0,0), Point(8,5), true);
437  extensionTest( dss, Point(9,7), Point(-2,1), nbok, nb );
438  }
439
440  if (nbok == nb)
441  {
442  trace.info() << "not compatible second step" << std::endl;
443  DSS dss(Point(0,0), Point(1,1), true);
444  extensionTest( dss, Point(0,2), Point(-1,1), nbok, nb );
445  }
446
447  if (nbok == nb)
448  {
449  trace.info() << "a third step" << std::endl;
450  DSS dss(Point(0,0), Point(2,1), true);
451  extensionTest( dss, Point(2,2), Point(0,1), nbok, nb );
452  }
453
454  if (nbok == nb)
455  {
456  trace.info() << "strongly exterior" << std::endl;
457  DSS dss(Point(0,0), Point(8,5), true);
458  extensionTest( dss, Point(9,6), Point(-1,0), nbok, nb );
459  }
460
461  if (nbok == nb)
462  {
463  trace.info() << "confounded points" << std::endl;
464  DSS dss(Point(0,0), Point(8,5), true);
465  extensionTest( dss, Point(8,5), Point(0,0), nbok, nb, 9 );
466  }
467
468  if (nbok == nb)
469  {
470  trace.info() << "strongly interior points" << std::endl;
471  DSS dss0(Point(0,0), Point(8,5), true);
472  DSS dss(5, 8, Point(-2,-2), Point(8,5),
473  dss0.Uf(), dss0.Ul(),
474  dss0.Lf(), dss0.Ll() );
475  extensionTest( dss, Point(9,5), Point(-3,-2), nbok, nb, 9 );
476  }
477
478  if (nbok == nb)
479  {
480  trace.info() << "weakly interior points on the left" << std::endl;
481  DSS dss0(Point(0,0), Point(8,5), true);
482  Point newPointToBack = dss0.Lf()-Vector(8,5);
483  Point newPointToFront = dss0.Ul()+Vector(8,5);
484  DSS dss(5, 8,
485  newPointToBack+dss0.steps().second,
486  newPointToFront-dss0.steps().second,
487  dss0.Uf(), dss0.Ul(),
488  dss0.Lf(), dss0.Ll()+Vector(8,5) );
489  extensionTest( dss, newPointToFront, newPointToBack, nbok, nb, 5 );
490  }
491
492  if (nbok == nb)
493  {
494  trace.info() << "weakly exterior points on the left" << std::endl;
495  DSS dss0(Point(0,0), Point(8,5), true);
496  Point newPointToBack = dss0.Uf()+dss0.shift()-Vector(8,5);
497  Point newPointToFront = dss0.Ll()-dss0.shift()+Vector(8,5);
498  DSS dss(5, 8,
499  newPointToBack+dss0.steps().second,
500  newPointToFront-dss0.steps().second,
501  dss0.Uf(), dss0.Ul(),
502  dss0.Lf()-Vector(8,5), dss0.Ll() );
503  extensionTest( dss, newPointToFront, newPointToBack, nbok, nb, 7 );
504  }
505
506  if (nbok == nb)
507  {
508  trace.info() << "weakly interior points on the right" << std::endl;
509  DSS dss0(Point(0,0), Point(8,5), true);
510  Point newPointToBack = dss0.Uf()-Vector(8,5);
511  Point newPointToFront = dss0.Ll()+Vector(8,5);
512  DSS dss(5, 8,
513  newPointToBack+dss0.steps().first,
514  newPointToFront-dss0.steps().first,
515  dss0.Uf(), dss0.Ul(),
516  dss0.Lf()-Vector(8,5), dss0.Ll() );
517  extensionTest( dss, newPointToFront, newPointToBack, nbok, nb, 6 );
518  }
519
520  if (nbok == nb)
521  {
522  trace.info() << "weakly exterior points on the right" << std::endl;
523  DSS dss0(Point(0,0), Point(8,5), true);
524  Point newPointToBack = dss0.Lf()-Vector(8,5)-dss0.shift();
525  Point newPointToFront = dss0.Ul()+Vector(8,5)+dss0.shift();
526  DSS dss(5, 8,
527  newPointToBack+dss0.steps().first,
528  newPointToFront-dss0.steps().first,
529  dss0.Uf(), dss0.Ul(),
530  dss0.Lf(), dss0.Ll()+Vector(8,5) );
531  extensionTest( dss, newPointToFront, newPointToBack, nbok, nb, 8 );
532  }
533
534  if (nbok == nb)
535  {
536  trace.info() << "first step" << std::endl;
537  DSS dss( Point(0,0), Point(0,0) );
538  extensionTest( dss, Point(1,0), Point(-1,0), nbok, nb, 1 );
539  }
540
541  if (nbok == nb)
542  {
543  trace.info() << "first step repetition" << std::endl;
544  DSS dss(Point(0,0), Point(1,0), true);
545  extensionTest( dss, Point(2,0), Point(-1,0), nbok, nb, 2 );
546  }
547
548  if (nbok == nb)
549  {
550  trace.info() << "second step (above)" << std::endl;
551  DSS dss0(Point(0,0), Point(2,1), true);
552  DSS dss(Point(0,0), Point(2,1) - dss0.steps().second);
553  Point newPointToBack = Point(0,0) - dss0.steps().second;
554  extensionTest( dss, Point(2,1), newPointToBack, nbok, nb, 3 );
555  }
556
557  if (nbok == nb)
558  {
559  trace.info() << "second step (below)" << std::endl;
560  DSS dss0a(Point(0,0), Point(2,-1), true);
561  DSS dss0b(Point(0,0), Point(2,1), true);
562  DSS dss(Point(0,0), Point(2,-1) - dss0a.steps().first);
563  Point newPointToBack = Point(0,0) - dss0a.steps().first;
564  extensionTest( dss, Point(2,-1), newPointToBack, nbok, nb, 4 );
565  }
566
567  trace.endBlock();
568
569  if (nbok == nb)
570  {
571  trace.beginBlock ( "Retraction services..." );
572
573  {
574  trace.info() << "upper leaning points" << std::endl;
575  DSS dss(Point(0,0), Point(8,5), true);
576  retractionTest( dss, nbok, nb );
577  }
578
579  if (nbok == nb)
580  {
581  trace.info() << "lower leaning points" << std::endl;
582  DSS dss0(Point(0,0), Point(8,5), true);
583  Point first = dss0.Lf();
584  Point last = dss0.Lf() + Vector(8,5);
585  DSS dss(5, 8, first, last,
586  Point(8,5), Point(8,5),
587  first, last );
588  retractionTest( dss, nbok, nb );
589  }
590
591  if (nbok == nb)
592  {
593  trace.info() << "upper leaning points (repetitions)" << std::endl;
594  DSS dss(Point(0,0), Point(16,10), true);
595  retractionTest( dss, nbok, nb );
596  }
597
598  if (nbok == nb)
599  {
600  trace.info() << "lower leaning points (repetitions)" << std::endl;
601  DSS dss0(Point(0,0), Point(16,10), true);
602  Point first = dss0.Lf();
603  Point last = dss0.Lf() + Vector(16,10);
604  DSS dss(5, 8, first, last,
605  Point(8,5), Point(16,10),
606  first, last );
607  retractionTest( dss, nbok, nb );
608  }
609
610  if (nbok == nb)
611  {
612  trace.info() << "no change" << std::endl;
613  DSS dss0(Point(0,0), Point(21,13), true);
614  typename DSS::ConstIterator itb = dss0.begin();
615  --itb; --itb; --itb;
616  typename DSS::ConstIterator ite = dss0.end();
617  ++ite; ++ite; ++ite;
618  DSS dss(dss0.a(), dss0.b(), *itb, *ite,
619  dss0.Uf(), dss0.Ul(), dss0.Lf(), dss0.Ll() );
620  retractionTest( dss, nbok, nb );
621  }
622
623  if (nbok == nb)
624  {
625  trace.info() << "one point" << std::endl;
626  DSS dss(Point(0,0), Point(0,0), true);
627  retractionTest( dss, nbok, nb, false );
628  }
629
630  if (nbok == nb)
631  {
632  trace.info() << "two points" << std::endl;
633  DSS dss(Point(0,0), Point(1,0), true);
634  retractionTest( dss, nbok, nb );
635  }
636
637  if (nbok == nb)
638  {
639  trace.info() << "from two steps to one step" << std::endl;
640  DSS dss(Point(0,0), Point(1,1), true);
641  retractionTest( dss, nbok, nb );
642  }
643
644
645  trace.endBlock();
646  }
647
648  return nbok == nb;
649 }
650
658 template <typename DSS>
659 bool compatibleStepsTest(const DSS& dss)
660 {
661  unsigned int nbok = 0;
662  unsigned int nb = 0;
663
664  trace.beginBlock ( "directional Position..." );
665
666  trace.info() << "shift: " << dss.shift()
667  << ", front pos: " << dss.position( dss.front() )
668  << ", back pos: " << dss.position( dss.back() ) << std::endl;
669  if ( dss.position( dss.front() )
670  > dss.position( dss.back() ) )
671  nbok++;
672  nb++;
673
674  trace.info() << "(" << nbok << "/" << nb << ") "
675  << std::endl;
676
677  trace.endBlock();
678
679  trace.beginBlock ( "Compatible steps..." );
680
682  DSS mdss = dss;
683  if ( mdss.extendFront(mdss.front()-dss.shift()+dss.steps().first) )
684  nbok++;
685  nb++;
686
687  trace.info() << "(" << nbok << "/" << nb << ") "
688  << std::endl;
689  mdss = dss;
690  if ( !mdss.extendFront(mdss.front()-dss.shift()) )
691  nbok++;
692  nb++;
693
694  trace.info() << "(" << nbok << "/" << nb << ") "
695  << std::endl;
696
697  mdss = dss;
698  if ( !mdss.extendFront(mdss.front()-dss.shift()-dss.steps().first) )
699  nbok++;
700  nb++;
701
702  trace.info() << "(" << nbok << "/" << nb << ") "
703  << std::endl;
704
706  mdss = dss;
707  if ( mdss.extendBack(mdss.back()+dss.shift()-dss.steps().first) )
708  nbok++;
709  nb++;
710
711  trace.info() << "(" << nbok << "/" << nb << ") "
712  << std::endl;
713  mdss = dss;
714  if ( !mdss.extendBack(mdss.back()+dss.shift()) )
715  nbok++;
716  nb++;
717
718  trace.info() << "(" << nbok << "/" << nb << ") "
719  << std::endl;
720
721  mdss = dss;
722  if ( !mdss.extendBack(mdss.back()+dss.shift()+dss.steps().first) )
723  nbok++;
724  nb++;
725
726  trace.info() << "(" << nbok << "/" << nb << ") "
727  << std::endl;
728
729  trace.endBlock();
730
731  return nbok == nb;
732 }
733
739 template <typename DSS>
740 bool constructorsTest()
741 {
742  BOOST_CONCEPT_ASSERT(( concepts::CPointPredicate<DSS> ));
743  BOOST_CONCEPT_ASSERT(( concepts::CConstBidirectionalRange<DSS> ));
744
745  typedef typename DSS::Point Point;
746
747  unsigned int nbok = 0;
748  unsigned int nb = 0;
749
750  trace.beginBlock ( "constructors..." );
751
752  {
753  //pattern
754  DSS dss0( Point(0,0), Point(8,5) );
755  trace.info() << dss0 << std::endl;
756
757  //construction by points range
758  DSS dss( dss0.begin(), dss0.end() );
759  trace.info() << dss << std::endl;
760
761  if ( (dss0.isValid())
762  &&(dss.isValid())
763  && (dss0 == dss)
764  && (dss.Lf() == dss.Ll())
765  && (dss.Uf() == dss.back())
766  && (dss.Ul() == dss.front())
767  && (dss.back() != dss.front()) )
768  nbok++;
769  nb++;
770  trace.info() << "(" << nbok << "/" << nb << ") "
771  << std::endl;
772
773  //reversed pattern
774  DSS rdss0( Point(0,0), Point(8,5), false );
775  trace.info() << rdss0 << std::endl;
776
777  //construction by points range
778  DSS rdss( rdss0.begin(), rdss0.end() );
779  trace.info() << rdss << std::endl;
780
781  if ( (rdss0.isValid())
782  &&(rdss.isValid())
783  && (rdss0 == rdss)
784  && (rdss.Uf() == rdss.Ul())
785  && (rdss.Lf() == rdss.back())
786  && (rdss.Ll() == rdss.front())
787  && (rdss.back() != rdss.front())
788  && (rdss != dss) )
789  nbok++;
790  nb++;
791  trace.info() << "(" << nbok << "/" << nb << ") "
792  << std::endl;
793
794  }
795
796  trace.endBlock();
797
798  return nbok == nb;
799 }
800
811 template <typename DSS>
813  typename DSS::Position x, typename DSS::Position y)
814 {
815  typename DSS::DSL dsl = aDSS.dsl();
816  DSS dss0( dsl.begin(dsl.getPoint(x)), dsl.end(dsl.getPoint(y)) ); //classical (linear-time)
817  DSS dss1( dsl, dsl.getPoint(x), dsl.getPoint(y) ); //smartCH (log)
818  DSS dss2( aDSS, dsl.getPoint(x), dsl.getPoint(y) ); //reversedSmartCH (log)
819  return ( (dss0 == dss1)&&(dss0 == dss2) );
820 }
821
832 template <typename DSL>
833 bool comparisonSubsegment(typename DSL::Coordinate a, typename DSL::Coordinate b)
834 {
835  unsigned int nbok = 0;
836  unsigned int nb = 0;
837
838  trace.beginBlock ( "Subsegment comparison ..." );
839
841  for (typename DSL::Integer mu = 0; ( (mu-1 >= -aDSL.omega())&&(nbok == nb) ); --mu)
842  {
843  //trace.info() << "mu=" << mu << std::endl;
844
845  typedef typename DSL::Point Point;
846  typedef typename DSL::Coordinate Coordinate;
847  typedef typename DSL::Integer Integer;
849
854
856
857  for (typename DSL::Position l = 0; ( (l <= 2*aDSL.patternLength())&&(nbok == nb) ); ++l)
858  {
859  //trace.info() << "l=" << l << std::endl;
860
861  for (typename DSL::Position k = 0; ( (k <= l)&&(nbok == nb) ); ++k)
862  {
863  //trace.info() << "k=" << k << std::endl;
864
865  if (comparisonSubsegment(dss, k, l))
866  nbok++;
867  nb++;
868
869  }
870  }
871
872  }
873
874  trace.endBlock();
875
876  return (nb == nbok);
877 }
878
879 //---------------------------------------------------------------------------
880 bool unionTest()
881 {
882  unsigned int nb = 0;
883  unsigned int nbok = 0;
884
886  typedef DSS::Point Point;
887
888  trace.beginBlock("Testing union of two DSSs");
889
890  // Different tests to cover all possible configurations
891
892  //-------------------------------------------------
893  //---------- Union is part of a DSL----------------
894
895  // DSS1 included in DSS2
896
897  trace.beginBlock("Simplest inclusion: DSS1 in DSS2");
898  // octant 0
899  trace.info() << "octant 0\n";
900  DSS DSS1(1,2,Point(2,2),Point(6,4),Point(2,2),Point(6,4),Point(3,2),Point(5,3));
901  DSS DSS2(3,5,Point(-2,-1),Point(9,6),Point(2,2),Point(7,5),Point(0,0),Point(5,3));
902  DSS res=DSS1.computeUnion(DSS2);
903  nb++;
904  nbok +=(res==DSS2)?1:0;
905
906  // octant 1
907  trace.info() << "octant 1\n";
908  DSS1 = DSS(2,1,Point(2,2),Point(4,6),Point(2,3),Point(3,5),Point(2,2),Point(4,6));
909  assert(DSS1.isValid());
910  DSS2 = DSS(5,3,Point(-1,-2),Point(6,9),Point(0,0),Point(3,5),Point(2,2),Point(5,7));
911  assert(DSS2.isValid());
912  res = DSS1.computeUnion(DSS2);
913  nb++;
914  nbok +=(res==DSS2)?1:0;
915
916  // octant 2
917  trace.info() << "octant 2\n";
918  DSS1 = DSS(2,-1,Point(-2,2),Point(-4,6),Point(-2,2),Point(-4,6),Point(-2,3),Point(-3,5));
919  assert(DSS1.isValid());
920  DSS2 = DSS(5,-3,Point(1,-2),Point(-6,9),Point(-2,2),Point(-5,7),Point(0,0),Point(-3,5));
921  assert(DSS2.isValid());
922  res = DSS1.computeUnion(DSS2);
923  nb++;
924  nbok +=(res==DSS2)?1:0;
925
926  // octant 3
927  trace.info() << "octant 3\n";
928  DSS1 = DSS(1,-2,Point(-2,2),Point(-6,4),Point(-3,2),Point(-5,3),Point(-2,2),Point(-6,4));
929  assert(DSS1.isValid());
930  DSS2 = DSS(3,-5,Point(2,-1),Point(-9,6),Point(0,0),Point(-5,3),Point(-2,2),Point(-7,5));
931  assert(DSS2.isValid());
932  res = DSS1.computeUnion(DSS2);
933  nb++;
934  nbok +=(res==DSS2)?1:0;
935
936  // octant 4
937  trace.info() << "octant 4\n";
938  DSS1 = DSS(-1,-2,Point(-2,-2),Point(-6,-4),Point(-2,-2),Point(-6,-4),Point(-3,-2),Point(-5,-3));
939  assert(DSS1.isValid());
940  DSS2 = DSS(-3,-5,Point(2,1),Point(-9,-6),Point(-2,-2),Point(-7,-5),Point(0,0),Point(-5,-3));
941  assert(DSS2.isValid());
942  res = DSS1.computeUnion(DSS2);
943  nb++;
944  nbok +=(res==DSS2)?1:0;
945
946  // octant 5 - take octant3 - DSS(a,b...) -> DSS(-a,b...) + Point(x,y) -> Point(x,-y) + inverse lower and upper leaning points
947
948  trace.endBlock();
949
950  // DSS2 included in DSS1 + see unionComparisonTest below
951  trace.beginBlock("Simplest inclusion: DSS2 in DSS1");
952  // octant 0
953  trace.info() << "octant 0\n";
954  DSS1 = DSS(3,5,Point(-2,-1),Point(9,6),Point(2,2),Point(7,5),Point(0,0),Point(5,3));
955  DSS2 = DSS(1,2,Point(2,2),Point(6,4),Point(2,2),Point(6,4),Point(3,2),Point(5,3));
956  res = DSS1.computeUnion(DSS2);
957  nb++;
958  nbok +=(res==DSS1)?1:0;
959
960  trace.endBlock();
961
962  // DSS2 belongs to DSS1's supporting DSL
963
964  trace.beginBlock("DSS2 belongs to DSS1's supporting DSL");
965  // octant 0
966  trace.info() << "octant 0 - no new leaning points\n";
967  DSS1 = DSS(3,7,Point(1,3),Point(12,7),Point(3,4),Point(10,7),Point(5,4),Point(12,7));
968  DSS2 = DSS(1,2,Point(14,8),Point(16,9),Point(15,9),Point(15,9),Point(14,8),Point(16,9));
969  res = DSS1.computeUnion(DSS2);
970  nb++;
971  nbok +=(res==DSS(3,7,Point(1,3),Point(16,9),Point(3,4),Point(10,7),Point(5,4),Point(12,7)))?1:0;
972  trace.info() << "(" << nbok << "/" << nb << ") "
973  << std::endl;
974
975  trace.info() << "octant 0 - new leaning points in DSS2\n";
976  DSS1 = DSS(3,7,Point(1,3),Point(10,7),Point(3,4),Point(10,7),Point(5,4),Point(5,4));
977  DSS2 = DSS(1,2,Point(12,7),Point(17,10),Point(13,8),Point(17,10),Point(12,7),Point(16,9));
978  res = DSS1.computeUnion(DSS2);
979  nb++;
980  nbok +=(res==DSS(3,7,Point(1,3),Point(17,10),Point(3,4),Point(17,10),Point(5,4),Point(12,7)))?1:0;
981  trace.info() << "(" << nbok << "/" << nb << ") "
982  << std::endl;
983
984  trace.info() << "octant 0 - new leaning points between DSS1 and DSS2\n";
985  DSS1 = DSS(3,7,Point(1,3),Point(10,7),Point(3,4),Point(10,7),Point(5,4),Point(5,4));
986  DSS2 = DSS(1,2,Point(13,8),Point(15,9),Point(13,8),Point(15,9),Point(14,8),Point(14,8));
987  res = DSS1.computeUnion(DSS2);
988  nb++;
989  nbok +=(res==DSS(3,7,Point(1,3),Point(15,9),Point(3,4),Point(10,7),Point(5,4),Point(12,7)))?1:0;
990  trace.info() << "(" << nbok << "/" << nb << ") "
991  << std::endl;
992
993  trace.endBlock();
994
995  // DSS1 belongs to DSS2 supporting DSL
996
997  // DSS1 and DSS2 connected and union is part of a DSL -> see
998  // unionComparisonTest below
999
1000  // DSS1 and DSS2 not connected but easy case and union is part of a
1001  // DSL -> see unionComparisonTest below
1002
1003  trace.beginBlock("Not connected but easy case");
1004
1005  trace.info() << "octant 2";
1006  DSS1 = DSS(1,5,Point(0,1),Point(5,2),Point(1,2),Point(1,2),Point(0,1),Point(5,2));
1007  DSS2 = DSS(1,4,Point(9,2),Point(14,3),Point(11,3),Point(11,3),Point(10,2),Point(14,3));
1008  res = DSS1.computeUnion(DSS2);
1009  nb++;
1010  nbok +=(res==DSS(1,10,Point(0,1),Point(14,3),Point(1,2),Point(11,3),Point(0,1),Point(10,2)))?1:0;
1011  trace.info() << "(" << nbok << "/" << nb << ") "
1012  << std::endl;
1013
1014  trace.endBlock();
1015
1016  // DSS1 and DSS2 not connected and union is part of a DSL
1017
1018  trace.beginBlock("Not connected case");
1019
1020  trace.info() << "octant 0\n";
1021  DSS1 = DSS(1,5,Point(0,1),Point(5,2),Point(1,2),Point(1,2),Point(0,1),Point(5,2));
1022  DSS2 = DSS(1,4,Point(9,2),Point(14,3),Point(11,3),Point(11,3),Point(10,2),Point(14,3));
1023  res = DSS1.computeUnion(DSS2);
1024  nb++;
1025  nbok +=(res==DSS(1,10,Point(0,1),Point(14,3),Point(1,2),Point(11,3),Point(0,1),Point(10,2)))?1:0;
1026  trace.info() << "(" << nbok << "/" << nb << ") "
1027  << std::endl;
1028
1029  DSS1 = DSS(1,6,Point(0,1),Point(6,2),Point(1,2),Point(1,2),Point(0,1),Point(6,2));
1030  DSS2 = DSS(0,1,Point(13,3),Point(18,3),Point(13,3),Point(18,3),Point(13,3),Point(18,3));
1031  res = DSS1.computeUnion(DSS2);
1032  nb++;
1033  nbok +=(res==DSS(1,9,Point(0,1),Point(18,3),Point(1,2),Point(10,3),Point(0,1),Point(18,3)))?1:0;
1034  trace.info() << "(" << nbok << "/" << nb << ") "
1035  << std::endl;
1036
1037  trace.info() << "octant 2\n";
1038
1039  DSS1 = DSS(6,-1,Point(-1,0),Point(-2,6),Point(-2,1),Point(-2,1),Point(-1,0),Point(-2,6));
1040  DSS2 = DSS(1,0,Point(-3,13),Point(-3,18),Point(-3,13),Point(-3,18),Point(-3,13),Point(-3,18));
1041  res = DSS1.computeUnion(DSS2);
1042  nb++;
1043  nbok +=(res==DSS(9,-1,Point(-1,0),Point(-3,18),Point(-2,1),Point(-3,10),Point(-1,0),Point(-3,18)))?1:0;
1044  trace.info() << "(" << nbok << "/" << nb << ") "
1045  << std::endl;
1046
1047
1048
1049  trace.endBlock();
1050
1051  //-------------------------------------------------
1052  //---------- Union is not part of a DSL -----------
1053
1054  trace.beginBlock("Union is not part of a DSL");
1055
1056  // DSS1 and DSS2 not in the same octant
1057  trace.info() << "DSS1 and DSS2 are not in the same octant\n";
1058
1059  DSS1 = DSS(1,3,Point(0,0),Point(3,1),Point(0,0),Point(3,1),Point(2,0),Point(2,0));
1060  DSS2 = DSS(1,-3,Point(6,2),Point(9,1),Point(6,2),Point(9,1),Point(8,2),Point(8,2));
1061  res = DSS1.computeUnion(DSS2);
1062  nb++;
1063  nbok +=(res==DSS(Point(0,0)))?1:0;
1064  trace.info() << "(" << nbok << "/" << nb << ") "
1065  << std::endl;
1066
1067  // DSS1 and DSS2 connected and union is not part of a DSL
1068  trace.info() << "DSS1 and DSS2 are in the same octant and connected\n";
1069
1070  DSS1 = DSS(1,3,Point(0,0),Point(4,2),Point(1,1),Point(4,2),Point(0,0),Point(3,1));
1071  DSS2 = DSS(1,5,Point(4,2),Point(9,3),Point(4,2),Point(9,3),Point(8,2),Point(8,2));
1072  res = DSS1.computeUnion(DSS2);
1073  nb++;
1074  nbok +=(res==DSS(Point(0,0)))?1:0;
1075  trace.info() << "(" << nbok << "/" << nb << ") "
1076  << std::endl;
1077
1078
1079  // DSS1 and DSS2 not connected but easy case and union is not part of a DSL
1080  trace.info() << "DSS1 and DSS1 are in the same octant, not connected but easy case anyway\n";
1081
1082  DSS1 = DSS(-3,-1,Point(0,0),Point(-2,-5),Point(0,0),Point(-1,-3),Point(-1,-1),Point(-2,-4));
1083  DSS2 = DSS(-3,-1,Point(-2,-8),Point(-3,-11),Point(-2,-10),Point(-2,-10),Point(-2,-8),Point(-3,-11));
1084  res = DSS1.computeUnion(DSS2);
1085  nb++;
1086  nbok +=(res==DSS(Point(0,0)))?1:0;
1087  trace.info() << "(" << nbok << "/" << nb << ") "
1088  << std::endl;
1089
1090  // DSS1 and DSS2 not connected and union is not part of a DSL
1091  trace.info() << "DSS1 and DSS2 are in the same octant but not connected\n";
1092
1093  DSS1 = DSS(-3,-1,Point(0,0),Point(-2,-5),Point(0,0),Point(-1,-3),Point(-1,-1),Point(-2,-4));
1094  DSS2 = DSS(-3,-1,Point(-5,-8),Point(-6,-11),Point(-5,-10),Point(-5,-10),Point(-5,-8),Point(-6,-11));
1095  res = DSS1.computeUnion(DSS2);
1096  nb++;
1097  nbok +=(res==DSS(Point(0,0)))?1:0;
1098  trace.info() << "(" << nbok << "/" << nb << ") "
1099  << std::endl;
1100
1101
1102  trace.endBlock();
1103
1104  return (nb==nbok);
1105
1106 }
1107
1108 int max(int a, int b)
1109 {
1110  return ((a>b)?a:b);
1111 }
1112
1113 // General random test of the union of two DSSs
1114 // - compare the result with ArithmeticalDSS recognition algorithm for easy cases (connected or first point of
1115 // DSS2 and last point of DSS1 have the same ordinate) and inclusion cases
1116 // - otherwise, check DSS result validity + check that computed leaning points belong to the DSL when they should (when they are between A and B or between C and D)
1117 template <typename TCoordinate,typename TInteger, unsigned short adjacency>
1118 //template <typename DSS>
1119 bool unionComparisonTest(int modb, int modx, unsigned int nbtries)
1120 {
1122  typedef typename DSS::DSL DSL;
1123  typedef typename DSS::Point Point;
1124  typedef typename DSS::Integer Integer;
1125  typedef typename DSS::Vector Vector;
1126
1127  unsigned int nb = 0;
1128  unsigned int nbok = 0;
1129  unsigned int nbEasy = 0;
1130
1132
1133  trace.beginBlock("General random test results");
1135
1136  for ( unsigned int i = 0; i < nbtries; ++i )
1137  {
1138  // Pick up a random DSL slope
1139  Integer b( rand() % modb + 1 );
1140  Integer a( rand() % b +1);
1141  while(ic.gcd(a,b) !=1)
1142  a =rand()%b +1; // |a| < |b|
1143
1144  // Pick-up random signs for a and b
1145  a = a*((rand()%2==0)?1:-1);
1146  b = b*((rand()%2==0)?1:-1);
1147
1148  if ( ic.gcd( a, b ) == 1 )
1149  {
1150
1151  for ( unsigned int j = 0; j < 5; ++j )
1152  {
1153  // Pick up the DSL intercept
1154  Integer mu = rand() % (2*modb);
1155  DSL baseDSL(a,b,-mu);
1156
1157  for (Integer x = 0; x < 10; ++x )
1158  {
1159  Integer elemMove = (b>0)?1:-1;
1160
1161  // modx modulates the length of the subsegments
1162  // Pick up the beginning of the first subsegment
1163  Integer x1 = rand() % modx;
1164  // Pick up the end of the first subsegment
1165  Integer x2 = x1 + (modx + (rand() % modx))*elemMove;
1166
1167  /************************************************/
1168
1169  // Connected DSSs: The beginning of the second
1170  //subsegment is randomly set between x1 and x2 or just
1171  //after x2.
1172  //Integer x3 = x1 + (rand() % (x2-x1+1))*elemMove;
1173
1174  // Disonnected DSSs: The beginning of the second subsegment is randomly set after x2.
1175  //Integer x3 = x2 + (rand() % (modb))*elemMove;
1176
1177  // General Case
1178  Integer x3 = x1 + (rand() % (2*modb))*elemMove;
1179
1180  // The length of the second segment is set to modx
1181  Integer x4 = x3 + modx*elemMove;
1182
1183  Integer y1,y2,y3,y4;
1184  if(baseDSL.shift()[1] < 0)
1185  {
1186  y1 = ic.floorDiv(a*x1+mu,b); y2 = ic.floorDiv(a*x2+mu,b);
1187  y3 = ic.floorDiv(a*x3+mu,b); y4 = ic.floorDiv(a*x4+mu,b);
1188  }
1189  else
1190  {
1191  y1 = ic.ceilDiv(a*x1+mu,b); y2 = ic.ceilDiv(a*x2+mu,b);
1192  y3 = ic.ceilDiv(a*x3+mu,b); y4 = ic.ceilDiv(a*x4+mu,b);
1193  }
1194
1195  Point A,B,C,D;
1197  //Randomly switch a and b to cover cases where |a| > |b|
1198  if(rand()%2)
1199  {
1201  A = Point(-y1,x1); B = Point(-y2,x2);
1202  C = Point(-y3,x3); D = Point(-y4,x4);
1203  }
1204  else
1205  {
1206  A = Point(x1,y1); B = Point(x2,y2);
1207  C = Point(x3,y3); D = Point(x4,y4);
1208  }
1209
1210  // Computation of the parameters of the two segments
1211  // using the subsegment algorithm of [Roussillon,
1212  // 2014]
1213
1216
1217  nb++;
1218  // Computation of DSS1 \cup DSS2 using the union algorithm [Sivignon, 2014]
1219  DSS DSSres = DSS1.computeUnion(DSS2);
1220
1221
1222  // Compare the result with Arithmetical DSS recognition algorithm for easy cases
1223  Vector dir;
1225  dir = Vector(0,1);
1226  else
1227  dir = Vector(1,0);
1228
1230  {
1231  nbEasy++;
1232  // Computation of DSS1 \cup DSS2 using the
1233  // Arithmetical DSS algorithm: add points from B++
1234  // until D
1235  DSS DSSGroundTruth(DSS1);
1236  if(aDSL.before(B,D)) // otherwise [CD] is included
1237  // in [AB]
1238  {
1239  typename DSS::ConstIterator itbegin = aDSL.begin(B);
1240  typename DSS::ConstIterator itend = aDSL.end(D);
1241  typename DSS::ConstIterator it = itbegin++;
1242  while(it != itend)
1243  {
1244  DSSGroundTruth.extendFront(*it);
1245  it++;
1246  }
1247  }
1248
1249  if(DSSres != DSSGroundTruth)
1250  {
1251
1252  trace.info() << "DSS1 " << DSS1 << "\n" << "DSS2 " << DSS2 << std::endl;
1253  trace.info() << DSSres << std::endl;
1254  trace.info() << DSSGroundTruth << std::endl;
1255  trace.info() << "------------------\n";
1256  }
1257  nbok+=(DSSres == DSSGroundTruth)?1:0;
1258
1259  }
1260  else
1261  { // for disconnected cases, check that all the leaning points of DSSres that are between A anb B or between C and D are in the DSL
1262
1263  bool error = false;
1265  error = true;
1267  error = true;
1269  error = true;
1271  error = true;
1272
1273  if(error || !DSSres.isValid() || DSSres==DSS(Point(0,0)))
1274  {
1275  trace.info() << "disconnected\n";
1276  trace.info() << "DSS1 " << DSS1 << "\n" << "DSS2 " << DSS2 << std::endl;
1277  trace.info() << DSSres << std::endl;
1278  trace.info() << "--------------------------------\n";
1279  }
1280  else
1281  nbok++;
1282
1283  }
1284
1285
1286  }
1287  }
1288
1289  }
1290  }
1291
1292
1293  trace.info() << "(" << nbok << "/" << nb << ") "
1294  << nbEasy << " easy cases." << std::endl;
1295  trace.endBlock();
1296  return (nb==nbok);
1297 }
1298
1299
1300
1301 //---------------------------------------------------------------------------
1302 bool createDSSTest()
1303 {
1304  unsigned int nb = 0;
1305  unsigned int nbok = 0;
1306
1307  trace.beginBlock("Testing creation of a DSS from direction vector, two endpoints and one upper leaning point");
1308
1310  typedef DSS8::Point Point;
1312  nb++;
1313  nbok += (Factory::createDSS(3,5,Point(-6,-4),Point(14,8),Point(5,3)) == DSS8(3,5,Point(-6,-4),Point(14,8),Point(-5,-3),Point(10,6),Point(-2,-2),Point(13,7)))?1:0;
1314
1315  nb++;
1316  nbok += (Factory::createDSS(3,5,Point(0,0),Point(14,8),Point(3,2)) == DSS8(3,5,Point(0,0),Point(14,8),Point(3,2),Point(13,8),Point(1,0),Point(11,6)))?1:0;
1317
1318  nb++;
1319  nbok += (Factory::createDSS(3,5,Point(-3,-2),Point(14,8),Point(3,2)) == DSS8(3,5,Point(-3,-2),Point(14,8),Point(-2,-1),Point(13,8),Point(1,0),Point(11,6)))?1:0;
1320
1321  nb++;
1322  nbok += (Factory::createDSS(3,5,Point(0,0),Point(14,8),Point(3,2)) == DSS8(3,5,Point(0,0),Point(14,8),Point(3,2),Point(13,8),Point(1,0),Point(11,6)))?1:0;
1323
1324  nb++;
1325  nbok += (Factory::createDSS(3,5,Point(0,0),Point(14,8),Point(3,2)) == DSS8(3,5,Point(0,0),Point(14,8),Point(3,2),Point(13,8),Point(1,0),Point(11,6)))?1:0;
1326
1327  trace.endBlock();
1328
1329  return (nb==nbok);
1330 }
1331
1332
1333 bool testPatchCreatePattern()
1334 {
1335  unsigned int nbok = 0;
1336  unsigned int nb = 0;
1337
1338  trace.beginBlock("Test patch bezoutVector/CreatePattern");
1339
1342  typedef DSS8::Point Point;
1343  DSS8 dss = Factory::createPattern(DSS8::Point(0,0), DSS8::Point(-1,-3));
1344  nb++;
1345  nbok += (dss == DSS8(-3,-1,Point(0,0), Point(-1,-3), Point(0,0), Point(-1,-3), Point(-1,-1), Point(-1,-1)));
1346
1347  dss = Factory::createPattern(DSS8::Point(0,0), DSS8::Point(10,-1));
1348  nb++;
1349  nbok += (dss == DSS8(-1,10, Point(0,0), Point(10,-1), Point(0,0), Point(10,-1), Point(1,-1), Point(1,-1)));
1350
1351  trace.endBlock();
1352
1353  return (nb == nbok);
1354
1355 }
1356
1357
1359 int main( int argc, char** argv )
1360 {
1361  trace.beginBlock ( "Testing class ArithmeticalDSS" );
1362  trace.info() << "Args:";
1363  for ( int i = 0; i < argc; ++i )
1364  trace.info() << " " << argv[ i ];
1365  trace.info() << endl;
1366
1367  //main operators
1368  bool res = mainTest<DGtal::ArithmeticalDSS<DGtal::int32_t> >()
1369 #ifdef WITH_BIGINTEGER
1371 #endif
1372  && mainTest<DGtal::NaiveDSS8<DGtal::int32_t> >()
1373  && mainTest<DGtal::StandardDSS4<DGtal::int32_t> >()
1374  ;
1375
1376  { //range services for 8 adjacency
1379  typedef DSS8::Point Point;
1380
1381  res = res
1382  && rangeTest( Factory::createPattern(Point(0,0), Point(8,5)) )
1383  && rangeTest( Factory::createPattern(Point(0,0), Point(5,8)) )
1384  && rangeTest( Factory::createPattern(Point(0,0), Point(-5,8)) )
1385  && rangeTest( Factory::createPattern(Point(0,0), Point(-8,5)) )
1386  && rangeTest( Factory::createPattern(Point(0,0), Point(-8,-5)) )
1387  && rangeTest( Factory::createPattern(Point(0,0), Point(-5,-8)) )
1388  && rangeTest( Factory::createPattern(Point(0,0), Point(5,-8)) )
1389  && rangeTest( Factory::createPattern(Point(0,0), Point(8,-5)) )
1390  && rangeTest( Factory::createPattern(Point(0,0), Point(1,0)) )
1391  && rangeTest( Factory::createPattern(Point(0,0), Point(-1,0)) )
1392  && rangeTest( Factory::createPattern(Point(0,0), Point(0,1)) )
1393  && rangeTest( Factory::createPattern(Point(0,0), Point(0,-1)) )
1394  && rangeTest( Factory::createPattern(Point(0,0), Point(1,1)) )
1395  && rangeTest( Factory::createPattern(Point(0,0), Point(-1,1)) )
1396  && rangeTest( Factory::createPattern(Point(0,0), Point(1,-1)) )
1397  && rangeTest( Factory::createPattern(Point(0,0), Point(-1,-1)) )
1398  && rangeTest( Factory::createReversedPattern(Point(0,0), Point(8,5)) )
1399  && rangeTest( Factory::createReversedPattern(Point(0,0), Point(5,8)) )
1400  ;
1401  }
1402
1403
1404  { //range services for 4 adjacency
1407  typedef DSS4::Point Point;
1408
1409  res = res
1410  && rangeTest( Factory::createPattern(Point(0,0), Point(8,5)) )
1411  && rangeTest( Factory::createPattern(Point(0,0), Point(5,8)) )
1412  && rangeTest( Factory::createPattern(Point(0,0), Point(-8,-5)) )
1413  && rangeTest( Factory::createPattern(Point(0,0), Point(-5,-8)) )
1414  && rangeTest( Factory::createPattern(Point(0,0), Point(5,-8)) )
1415  && rangeTest( Factory::createPattern(Point(0,0), Point(8,-5)) )
1416  && rangeTest( Factory::createPattern(Point(0,0), Point(1,0)) )
1417  && rangeTest( Factory::createPattern(Point(0,0), Point(-1,0)) )
1418  && rangeTest( Factory::createPattern(Point(0,0), Point(0,1)) )
1419  && rangeTest( Factory::createPattern(Point(0,0), Point(0,-1)) )
1420  && rangeTest( Factory::createReversedPattern(Point(0,0), Point(8,5)) )
1421  ;
1422  }
1423
1424  {
1427  typedef DSS8::Point Point;
1428  res = res
1429  && compatibleStepsTest( Factory::createPattern(Point(0,0), Point(5,0)) )
1430  && compatibleStepsTest( Factory::createPattern(Point(0,0), Point(-5,0)) )
1431  && compatibleStepsTest( Factory::createPattern(Point(0,0), Point(0,5)) )
1432  && compatibleStepsTest( Factory::createPattern(Point(0,0), Point(0,-5)) )
1433  && compatibleStepsTest( Factory::createPattern(Point(0,0), Point(5,5)) )
1434  && compatibleStepsTest( Factory::createPattern(Point(0,0), Point(5,-5)) )
1435  && compatibleStepsTest( Factory::createPattern(Point(0,0), Point(-5,5)) )
1436  && compatibleStepsTest( Factory::createPattern(Point(0,0), Point(-5,-5)) )
1437  ;
1438  }
1439
1440  {
1443  typedef DSS4::Point Point;
1444  res = res
1445  && compatibleStepsTest( Factory::createPattern(Point(0,0), Point(5,0)) )
1446  && compatibleStepsTest( Factory::createPattern(Point(0,0), Point(-5,0)) )
1447  && compatibleStepsTest( Factory::createPattern(Point(0,0), Point(0,5)) )
1448  && compatibleStepsTest( Factory::createPattern(Point(0,0), Point(0,-5)) )
1449  ;
1450  }
1451
1452  res = res
1453  && updateTest<DGtal::ArithmeticalDSS<DGtal::int32_t> >()
1454 #ifdef WITH_BIGINTEGER
1456 #endif
1457  ;
1458
1459  res = res
1460  && constructorsTest<DGtal::ArithmeticalDSS<DGtal::int32_t> >()
1461 #ifdef WITH_BIGINTEGER
1463 #endif
1464  && constructorsTest<DGtal::NaiveDSS8<DGtal::int32_t> >()
1465  && constructorsTest<DGtal::StandardDSS4<DGtal::int32_t> >()
1466  ;
1467
1468  { //subsegment
1469  res = res
1470  && comparisonSubsegment<NaiveDSL<DGtal::int32_t> >(5,8)
1471  && comparisonSubsegment<NaiveDSL<DGtal::int32_t> >(8,13)
1472  && comparisonSubsegment<NaiveDSL<DGtal::int32_t> >(12,29)
1473  && comparisonSubsegment<NaiveDSL<DGtal::int32_t> >(8,5)
1474  && comparisonSubsegment<NaiveDSL<DGtal::int32_t> >(-5,8)
1475  && comparisonSubsegment<NaiveDSL<DGtal::int32_t> >(-8,5)
1476  && comparisonSubsegment<NaiveDSL<DGtal::int32_t> >(5,-8)
1477  && comparisonSubsegment<NaiveDSL<DGtal::int32_t> >(8,-5)
1478  && comparisonSubsegment<NaiveDSL<DGtal::int32_t> >(-5,-8)
1479  && comparisonSubsegment<NaiveDSL<DGtal::int32_t> >(-8,-5)
1480
1481  && comparisonSubsegment<StandardDSL<DGtal::int32_t> >(5,8)
1482  && comparisonSubsegment<StandardDSL<DGtal::int32_t> >(8,5)
1483  && comparisonSubsegment<StandardDSL<DGtal::int32_t> >(-5,8)
1484  && comparisonSubsegment<StandardDSL<DGtal::int32_t> >(-8,5)
1485  && comparisonSubsegment<StandardDSL<DGtal::int32_t> >(5,-8)
1486  && comparisonSubsegment<StandardDSL<DGtal::int32_t> >(8,-5)
1487  && comparisonSubsegment<StandardDSL<DGtal::int32_t> >(-5,-8)
1488  && comparisonSubsegment<StandardDSL<DGtal::int32_t> >(-8,-5)
1489 #ifdef WITH_BIGINTEGER
1490  && comparisonSubsegment<StandardDSL<DGtal::int32_t, DGtal::BigInteger> >(5,8)
1491 #endif
1492  ;
1493  }
1494
1495  { // createDSS
1496  res = res && createDSSTest();
1497  }
1498
1499  { // Patch BezoutVector / CreatePattern
1500  res = res && testPatchCreatePattern();
1501  }
1502
1503  { // union of two DSSs
1504  res = res && unionTest();
1505  res = res && unionComparisonTest<DGtal::int64_t,DGtal::int64_t,8>(43577,1276,2000);
1506  res = res && unionComparisonTest<DGtal::int64_t, DGtal::int64_t, 4>(86731,6648,2000);
1507  }
1508
1509
1510  trace.emphase() << ( res ? "Passed." : "Error." ) << endl;
1511  trace.endBlock();
1512  return res ? 0 : 1;
1513 }
1514 // //
void beginBlock(const std::string &keyword="")
Aim: Defines the concept describing a bidirectional const range.
DGtal::int32_t Integer
Definition: StdDefs.h:74
Trace trace
Definition: Common.h:130
static TInteger norm(const TInteger &a, const TInteger &b)
STL namespace.
double endBlock()
Aim: This class is an alias of ArithmeticalDSS for naive DSL. It represents a naive digital straight ...
MessageStream error
Aim: Defines a predicate on a point.
std::ostream & emphase()
Aim: This class represents a standard digital straight segment (DSS), ie. the sequence of simply 4-co...
Integer floorDiv(IntegerParamType na, IntegerParamType nb) const
Go to http://www.boost.org/doc/libs/1_52_0/libs/iterator/doc/BidirectionalTraversal.html.
Aim: Set of static methods that create digital straight segments (DSS) from some input parameters...
Aim: This class is an alias of ArithmeticalDSS for standard DSL. It represents a standard digital str...
Aim: This class represents a naive (resp. standard) digital straight segment (DSS), ie. the sequence of simply 8- (resp. 4-)connected digital points contained in a naive (resp. standard) digital straight line (DSL) between two points of it.
DGtal is the top-level namespace which contains all DGtal functions and types.
Integer dotProduct(const Vector2I &u, const Vector2I &v) const
std::ostream & info()
Integer gcd(IntegerParamType a, IntegerParamType b) const
Integer ceilDiv(IntegerParamType na, IntegerParamType nb) const