DGtal  0.6.devel
 All Data Structures Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Groups Pages
CombinatorialDSS.ih
1 
30 
31 #include <cstdlib>
33 
35 // IMPLEMENTATION of inline methods.
37 
38 
39 
41 // ----------------------- Standard services ------------------------------
42 
43 template < typename TConstIterator, typename TInteger >
44 inline
46 { }
47 
48 
49 template < typename TConstIterator, typename TInteger >
50 inline
52 { }
53 
54 
55 
56 
57 template < typename TConstIterator, typename TInteger >
58 inline
59 void
61  const ConstIterator & it,
62  const Point & start,
63  Vector (*displacements) (Code) )
64 {
65  myCodeHandler.init( it );
66  myFirstLetter = 0;
67 
68  myBegin = it;
69  myEnd = it;
70  ++myEnd;
71 
72  myLastLetter = 0;
73  myPatternBegin = 0;
74  myPatternEnd = 0;
75  myLeftPatternLength = 0;
76  myNextBefore =0;
77  myNextAfter = 0;
78  myNbRepeat = 1;
79 
80  myDisplacements = displacements;
81 
82  myFirstPoint = start;
83  myLastPoint = myFirstPoint + displacement( getCode( myFirstLetter) );
84 
85 }
86 
87 
88 
89 template < typename TConstIterator, typename TInteger >
90 inline
92 {
93  *this = *( i.getDSS() );
94 }
95 
96 
97 
98 template < typename TConstIterator, typename TInteger >
99 inline
101 {
102  init( fc.chain.begin(), fc.firstPoint(), FreemanChainCode::displacement );
103 }
104 
105 
106 
107 template < typename TConstIterator, typename TInteger >
108 inline
110 {
111  std::string::const_iterator string_it = it.getChain()->chain.begin();
112  string_it += it.getPosition();
113  init( string_it, *it, FreemanChainCode::displacement );
114 }
115 
116 
120 template < typename TConstIterator, typename TInteger >
121 inline
123  myCodeHandler ( other.myCodeHandler ),
124  myBegin ( other.myBegin ),
125  myEnd ( other.myEnd ),
126  myFirstPoint ( other.myFirstPoint ),
127  myLastPoint ( other.myLastPoint ),
128  myFirstLetter ( other.myFirstLetter ),
129  myLastLetter ( other.myLastLetter ),
130  myNbRepeat ( other.myNbRepeat ),
131  myPatternBegin ( other.myPatternBegin ),
132  myPatternEnd ( other.myPatternEnd ),
133  myLeftPatternLength ( other.myLeftPatternLength ),
134  myNextBefore ( other.myNextBefore ),
135  myNextAfter ( other.myNextAfter ),
136  myDisplacements ( other.myDisplacements )
137 {}
138 
139 
144 template < typename TConstIterator, typename TInteger >
145 inline
148 {
149  myCodeHandler = other.myCodeHandler;
150  myBegin = other.myBegin;
151  myEnd = other.myEnd;
152  myFirstPoint = other.myFirstPoint;
153  myLastPoint = other.myLastPoint;
154  myFirstLetter = other.myFirstLetter;
155  myLastLetter = other.myLastLetter;
156  myNbRepeat = other.myNbRepeat;
157  myPatternBegin = other.myPatternBegin ;
158  myPatternEnd = other.myPatternEnd;
159  myLeftPatternLength = other.myLeftPatternLength;
160  myNextBefore = other.myNextBefore;
161  myNextAfter = other.myNextAfter;
162  myDisplacements = other.myDisplacements;
163  return *this;
164 }
165 
166 
167 template < typename TConstIterator, typename TInteger >
168 inline
171 {
172  return CombinatorialDSS( );
173 }
174 
178 template < typename TConstIterator, typename TInteger >
179 inline
181 {
182  return ( ( begin() == other.begin() ) && ( end() == other.end() ) );
183 }
184 
185 
191 template < typename TConstIterator, typename TInteger >
192 inline
194 {
195  return !(*this == other);
196 }
197 
198 
199 template < typename TConstIterator, typename TInteger >
200 inline
203 {
204  return Reverse();
205 }
206 
207 
208 
212 template < typename TConstIterator, typename TInteger >
213 inline
215 {
216  Code letterRead = getCode( myLastLetter + 1 );
217  Code letterExpected = getCode( myNextAfter );
218 
219  // Test if the new letter forms a longer prefix of the main pattern
220  // If the new letter is not what was expected, either the main pattern
221  // has to grow or either the DSS may not be extended.
222  if ( letterRead == letterExpected ) {
223  // Test if it is a complete repetition of the main pattern
224  if ( myNextAfter == myPatternEnd ) {
225  ++myNbRepeat;
226  myNextAfter = myPatternBegin;
227  } else {
228  ++myNextAfter;
229  }
230 
231  } else if ( isTrivial() ) {
232  myLeftPatternLength = 1;
233  myNbRepeat = 1;
234  myPatternEnd = myLastLetter + 1;
235  myNextBefore = myPatternEnd;
236 
237  } else if ( nextIsLL( myNextAfter ) && ( letterRead == getBigLetter() ) ) {
238  // The previous main pattern is now the left subpattern
239  myLeftPatternLength = mainPatternLength();
240  myNbRepeat = 1;
241  Size myOldSuffixLength = suffixLength();
242  myPatternEnd = myLastLetter + 1;
243  myNextBefore = myPatternEnd - myOldSuffixLength;
244  myNextAfter = myPatternBegin;
245 
246  } else if ( isUL( myNextAfter ) && ( letterRead == getSmallLetter() ) ) {
247  //In this case thw whole main pattern is modified! Not only complexified.
248  Size myOldLeftPatternLength = myLeftPatternLength;
249  Size myOldSuffixLength = suffixLength();
250  myNbRepeat = 1;
251  myLeftPatternLength = mainPatternLength();
252  myPatternEnd = myLastLetter + 1;
253 
254  // test if the suffix is long enough to contain the new first upper
255  // leaning point (beginning of the main pattern)
256  if ( myOldSuffixLength < myOldLeftPatternLength ) {
257  myPatternBegin = myPatternBegin + myLeftPatternLength
258  - myOldLeftPatternLength;
259  myNextBefore = myPatternEnd - myLeftPatternLength +
260  myOldLeftPatternLength - myOldSuffixLength;
261  } else {
262  //TODO : test this!
263  myPatternBegin = myPatternBegin - myOldLeftPatternLength;
264  myNextBefore = myPatternEnd - (myOldSuffixLength - myOldLeftPatternLength);
265  }
266  myNextAfter = myPatternBegin;
267 
268  } else {
269  return false;
270  }
271  ++myEnd;
272  ++myLastLetter;
273  myLastPoint += displacement( getCode( myLastLetter ) );
274  return true;
275 }
276 
277 
281 template < typename TConstIterator, typename TInteger >
282 inline
284 {
285  Code letterRead = getCode( myFirstLetter - 1 );
286  Code letterExpected = getCode( myNextBefore );
287 
288  // Test if the new letter forms a longer suffix of the main pattern
289  // If the new letter is not what was expected, either the main pattern
290  // has to grow or either the DSS may not be extended.
291  if ( letterRead == letterExpected ) {
292  // Test if it forms a complete repetition of the main pattern
293  if ( myNextBefore == myPatternBegin ) {
294  //cout << "Case 1" << endl;
295  ++myNbRepeat;
296  // Move main pattern one iteration backward, nb 'myNextBefore' is
297  // already one iteration before.
298  Size mpl = mainPatternLength();
299  myPatternBegin -= mpl;
300  myPatternEnd -= mpl;
301  myNextAfter -= mpl;
302  myNextBefore = myPatternEnd;
303  } else {
304  --myNextBefore;
305  //cout << "Case 2" << endl;
306  }
307 
308 
309  } else if ( isTrivial() ) {
310  //cout << "Case 3" << endl;
311  myLeftPatternLength = myNbRepeat;
312  myPatternEnd += myNbRepeat-1;
313  myNbRepeat = 1;
314  myPatternBegin = myFirstLetter - 1;
315  myNextBefore = myPatternEnd;
316  myNextAfter = myPatternBegin;
317 
318  } else if ( previousIsLL( myNextBefore ) && ( letterRead == getSmallLetter() ) ) {
319  //cout << "Case 4" << endl;
320  // The previous main pattern is now the left subpattern
321  Size myOldMainPatternLength = mainPatternLength();
322  Size myOldLeftPatternLength = myLeftPatternLength;
323  //Size myOldRightPatternLength = myOldMainPatternLength - myOldLeftPatternLength;
324 
325  myPatternBegin = myFirstLetter - 1;
326  myPatternEnd += (myNbRepeat-1) * myOldMainPatternLength;
327  myLeftPatternLength = mainPatternLength() - myOldMainPatternLength;
328  myNbRepeat = 1;
329  myNextBefore = myPatternEnd;
330  myNextAfter -= myOldLeftPatternLength;
331 
332  } else if ( isUL( myNextBefore ) && ( letterRead == getBigLetter() ) ) {
333  //In this case the whole main pattern is modified! Not only complexified.
334  Size myOldMainPatternLength = mainPatternLength();
335  Size myOldRightPatternLength = myOldMainPatternLength - myLeftPatternLength;
336  Size myOldPrefixLength = prefixLength();
337 
338  myPatternBegin = myFirstLetter - 1;
339 
340  // test if the prefix is long enough to contain the new Last Upper
341  // Leaning point
342  if ( myOldPrefixLength < myOldRightPatternLength ) {
343  //cout << "Case 5" << endl;
344  myNextAfter = myNextAfter - myOldMainPatternLength + myLeftPatternLength;
345  myPatternEnd = myPatternEnd
346  + (myNbRepeat - 1)*myOldMainPatternLength
347  - myLeftPatternLength;
348 
349  } else {
350  //cout << "Case 6" << endl;
351  myNextAfter = myNextAfter - myOldMainPatternLength - myOldRightPatternLength;
352  myPatternEnd = myPatternEnd
353  + myNbRepeat*myOldMainPatternLength
354  - myLeftPatternLength;
355  }
356  myNbRepeat = 1;
357  myNextBefore = myPatternEnd;
358  myLeftPatternLength = mainPatternLength() - myOldMainPatternLength;
359 
360  } else {
361  //cout << "Case 7" << endl;
362  return false;
363  }
364  --myBegin;
365  --myFirstLetter;
366  myFirstPoint -= displacement( getCode( myFirstLetter ) );
367  return true;
368 }
369 
370 
371 
375 template < typename TConstIterator, typename TInteger >
376 inline
378 {
379 
380  if ( myNextBefore != myPatternEnd ) {
381  //Normal case
382  //cout << "Case 1" << endl;
383  ++myNextBefore;
384 
385  } else if ( isTrivial() ) {
386  // In this case, it can be shorten only if there is more than one
387  // repetition.
388  //cout << "Case 2" << endl;
389  if ( myNbRepeat == 1 ) return false;
390  myPatternBegin = myPatternEnd = myNextBefore = ++myNextAfter;
391  --myNbRepeat;
392 
393  } else if ( myNbRepeat >= 2 ) {
394  // Got more than one repetition, it suffices to consider the next
395  // repetition of the main pattern with one less repetition.
396  //cout << "Case 3" << endl;
397  Size myOldMainPatternLength = mainPatternLength();
398  myPatternBegin += myOldMainPatternLength;
399  myPatternEnd += myOldMainPatternLength;
400  myNextAfter += myOldMainPatternLength;
401  myNextBefore = myPatternBegin;
402  --myNbRepeat;
403 
404  } else {
405  //Only one repetition, the slope is modified.
406  Size myOldMainPatternLength = mainPatternLength();
407  Size myOldLeftPatternLength = myLeftPatternLength;
408  Size myOldRightPatternLength = myOldMainPatternLength - myOldLeftPatternLength;
409 
410  if ( prefixLength() >= myOldRightPatternLength ) {
411  // A second Lower Leaning Point has been read in the prefix at
412  // the end of the main pattern. The slope is simply reversed.
413  //cout << "Case 4" << endl;
414  myLeftPatternLength = myOldRightPatternLength;
415  myPatternBegin += myOldRightPatternLength;
416  myPatternEnd += myOldRightPatternLength;
417  myNextBefore = myPatternEnd - myOldRightPatternLength + 1;
418 
419  } else if ( myOldLeftPatternLength < myOldRightPatternLength ) {
420  // Remove one repetition of the left Berstel pattern.
421  //cout << "Case 5" << endl;
422  myPatternBegin += myOldLeftPatternLength;
423  myNextBefore -= ( myOldLeftPatternLength - 1 );
424  myNextAfter += myOldLeftPatternLength;
425 
426  } else if ( myOldLeftPatternLength > myOldRightPatternLength ) {
427  // The complexity of the slope is modified.
428  //cout << "Case 6" << endl;
429  Size myNbBerstelRight = (myOldRightPatternLength > 1) ?
430  myOldMainPatternLength / myOldRightPatternLength :
431  myOldMainPatternLength - 1;
432  Size myBerstelLeftLength = myOldMainPatternLength -
433  ( myNbBerstelRight * myOldRightPatternLength );
434  // Right subpattern becomes the main pattern
435  myNbRepeat = myNbBerstelRight;
436  myPatternBegin += myBerstelLeftLength;
437  myPatternEnd = myPatternBegin + myOldRightPatternLength - 1;
438  myNextBefore = myPatternEnd - myBerstelLeftLength + 1;
439  myNextAfter += myBerstelLeftLength;
440  myLeftPatternLength = (myPatternBegin == myPatternEnd) ?
441  0 : myBerstelLeftLength;
442 
443  } else {
444  // Special case of slope 1/1 with no prefix read, only a trivial
445  // DSS remains.
446  //cout << "Case 7" << endl;
447  myNextBefore = myNextAfter = myPatternBegin = myPatternEnd;
448  myLeftPatternLength = 0;
449  }
450  }
451 
452  ++myBegin;
453  myFirstPoint += displacement( getCode( myFirstLetter ) );
454  ++myFirstLetter;
455  return true;
456 }
457 
458 
462 template < typename TConstIterator, typename TInteger >
463 inline
465 {
466  if ( myNextAfter != myPatternBegin ) {
467  // Normal case
468  //cout << "Case 1" << endl;
469  --myNextAfter;
470 
471  } else if ( isTrivial() ) {
472  // In this case, it can be shorten only if there is more than one
473  // repetition.
474  //cout << "Case 2" << endl;
475  if ( myNbRepeat == 1 ) return false;
476  --myNbRepeat;
477 
478  } else if ( myNbRepeat >= 2 ) {
479  // Got more than one repetition, it suffices to consider the next
480  // repetition of the main pattern with one less repetition.
481  //cout << "Case 3" << endl;
482  --myNbRepeat;
483  myNextAfter = myPatternEnd;
484 
485  } else {
486  //Only one repetition, the slope is modified.
487  Size myOldMainPatternLength = mainPatternLength();
488  Size myOldLeftPatternLength = myLeftPatternLength;
489  Size myOldRightPatternLength = myOldMainPatternLength -
490  myOldLeftPatternLength;
491 
492  if ( suffixLength() >= myOldLeftPatternLength ) {
493  // A second Lower Leaning Point has been read in the suffix at
494  // the front of the main pattern. The slope is simply reversed.
495  //cout << "Case 4" << endl;
496  myLeftPatternLength = myOldRightPatternLength;
497  myPatternBegin -= myOldLeftPatternLength;
498  myPatternEnd -= myOldLeftPatternLength;
499  myNextAfter = myPatternBegin + myOldLeftPatternLength - 1;
500 
501  } else if ( myOldLeftPatternLength > myOldRightPatternLength ) {
502  // Remove one repetition of the right Berstel pattern.
503  //cout << "Case 5" << endl;
504  myPatternEnd -= myOldRightPatternLength;
505  myNextAfter += ( myOldRightPatternLength - 1 );
506  myNextBefore -= myOldRightPatternLength;
507  myLeftPatternLength -= myOldRightPatternLength;
508 
509  } else if ( myOldLeftPatternLength < myOldRightPatternLength ) {
510  // The complexity of the slope is modified.
511  //cout << "Case 6" << endl;
512  Size myNbBerstelLeft = (myOldLeftPatternLength > 1) ?
513  myOldMainPatternLength / myOldLeftPatternLength :
514  myOldMainPatternLength - 1;
515  Size myBerstelRightLength = myOldMainPatternLength -
516  ( myNbBerstelLeft * myOldLeftPatternLength );
517  Size myOldSuffixLength = suffixLength();
518 
519  // Left subpattern becomes the main pattern.
520  myNbRepeat = myNbBerstelLeft;
521  myLeftPatternLength = myOldLeftPatternLength - myBerstelRightLength;
522  myPatternEnd = myPatternBegin + myOldLeftPatternLength - 1;
523  myNextBefore = myPatternEnd - myOldSuffixLength;
524  myNextAfter = myPatternBegin + myBerstelRightLength - 1;
525 
526  } else {
527  // Special case of slope 1/1 with no prefix read, only a trivial
528  // DSS remains.
529  //cout << "Case 7" << endl;
530  myNextBefore = myNextAfter = myPatternEnd = myPatternBegin;
531  myLeftPatternLength = 0;
532  }
533  }
534  --myEnd;
535  myLastPoint -= displacement( getCode( myLastLetter ) );
536  --myLastLetter;
537  return true;
538 }
539 
540 
544 template < typename TConstIterator, typename TInteger >
545 inline
547 {
548  Code letterRead = getCode( myLastLetter + 1 );
549  Code letterExpected = getCode( myNextAfter );
550  if ( letterRead == letterExpected )
551  {
552  return true;
553  }
554  else if ( isTrivial() )
555  {
556  return true;
557  }
558  else if ( nextIsLL( myNextAfter ) && ( letterRead == getBigLetter() ) )
559  {
560  return true;
561  }
562  else if ( isUL( myNextAfter ) && ( letterRead == getSmallLetter() ) )
563  {
564  return true;
565  }
566  return false;
567 }
568 
569 
570 
574 template < typename TConstIterator, typename TInteger >
575 inline
577 {
578  Code letterRead = getCode( myFirstLetter - 1);
579  Code letterExpected = getCode( myNextBefore );
580  if ( letterRead == letterExpected )
581  {
582  return true;
583  }
584  else if ( isTrivial() )
585  {
586  return true;
587  }
588  else if ( previousIsLL( myNextBefore ) && ( letterRead == getSmallLetter() ) )
589  {
590  return true;
591  }
592  else if ( isUL( myNextBefore ) && ( letterRead == getBigLetter() ) )
593  {
594  return true;
595  }
596  return false;
597 }
598 
599 template < typename TConstIterator, typename TInteger >
600 inline
603 {
604  Vector v = myLastPoint - myFirstPoint;
605  myFirstPoint = p;
606  myLastPoint = p+v;
607 }
608 
609 
610 template < typename TConstIterator, typename TInteger >
611 inline
614 {
615  myFirstPoint += v;
616  myLastPoint += v;
617 }
618 
619 
623 template < typename TConstIterator, typename TInteger >
624 inline
626 {
627  return (
628  ( myFirstLetter <= myPatternBegin ) &&
629  ( myPatternBegin <= myPatternEnd ) &&
630  ( myPatternEnd <= myLastLetter ) &&
631  ( myNextBefore >= myPatternBegin ) &&
632  ( myNextBefore <= myPatternEnd ) &&
633  ( myNextAfter >= myPatternBegin ) &&
634  ( myNextAfter <= myPatternEnd ) &&
635  ( (myLeftPatternLength == 0 ) ||
636  (myLeftPatternLength < mainPatternLength() ) ) );
637 }
638 
640 // Interface - public :
641 
647 template < typename TConstIterator, typename TInteger >
648 inline
649 void
651 {
652  std::string s;
653  for (int i=myFirstLetter; i<= myLastLetter; i++)
654  s += getCode( i );
655  s += ".";
656  for (int i=myLastLetter+1; i<myLastLetter+4 ; i++)
657  s += getCode( i );
658  Integer a,b,mu,omega;
659  getArithmeticalDescription(a,b,mu,omega);
660  out << "[CombinatorialDSS]\n";
661  out << "myCodes = " << s << "\n";
662  out << "myFirstPoint = " << myFirstPoint << "\n";
663  out << "myLastPoint = " << myLastPoint << "\n";
664  out << "myFirstLetter = " << myFirstLetter << "\n";
665  out << "myLastLetter = " << myLastLetter << "\n";
666  out << "myNbRepeat = " << myNbRepeat << "\n";
667  out << "myPatternBegin = " << myPatternBegin << "\n";
668  out << "myPatternEnd = " << myPatternEnd << "\n";
669  out << "myLeftPatternLength = " << myLeftPatternLength << "\n";
670  out << "myNextBefore = " << myNextBefore << "\n";
671  out << "myNextAfter = " << myNextAfter << "\n";
672  out << "(a,b,mu,omega) = (" << a << ", " << b << ", " << mu << ", " <<
673  omega << ")\n";
674  out << "[End CombinatorialDSS]" << endl;
675 }
676 
677 
678 
679 
680 
682 // Implementation of inline functions //
683 
684 template < typename TConstIterator, typename TInteger >
685 inline
686 std::ostream&
687 DGtal::operator<< ( std::ostream & out,
689 {
690  object.selfDisplay( out );
691  return out;
692 }
693 
694 
698 template < typename TConstIterator, typename TInteger >
699 inline
700 //DGtal::CombinatorialDSS<TConstIterator,TInteger>::Code
703 {
704  return getCode( myPatternBegin );
705 }
706 
707 
711 template < typename TConstIterator, typename TInteger >
712 inline
715 {
716  return getCode( myPatternEnd );
717 }
718 
719 
720 /*
721  * @param a position in the FreemanChain
722  * @returns the letter at the given position
723  */
724 /*
725  * template <typename TInteger>
726  * inline
727  * typename DGtal::CombinatorialDSS<TConstIterator,TInteger>::Code
728  * DGtal::CombinatorialDSS<TConstIterator,TInteger>::getCode(Index pos) const
729  * {
730  * int fcSize = (int) myFC->size();
731  * if ( pos < 0 )
732  * pos += ( -(pos / fcSize) + 1) * fcSize;
733  * if ( pos >= fcSize )
734  * pos -= ( pos / fcSize) * fcSize;
735  * return myFC->code(pos);
736  * }
737  */
738 
739 template < typename TConstIterator, typename TInteger >
740 inline
743 {
744  return myCodeHandler.getCode( pos );
745 }
746 
747 template < typename TConstIterator, typename TInteger >
748 inline
751 {
752  return myCodeHandler.getCode( pos );
753 }
754 
755 
756 
761 template < typename TConstIterator, typename TInteger >
762 inline
765 {
766  return myPatternEnd - myPatternBegin + 1;
767 }
768 
773 template < typename TConstIterator, typename TInteger >
774 inline
777 {
778  ConstPointIterator it = pointBegin();
779  while ( ! isUL ( it.getIndex() ) )
780  ++it;
781  Point p_uf = *it;
782  ++it; /* At least one letter in the pattern */
783  if ( ! isTrivial() )
784  {
785  while ( ! isUL ( it.getIndex() ) )
786  ++it;
787  ++it;
788  }
789  return *it - p_uf;
790 }
791 
792 
796 template < typename TConstIterator, typename TInteger >
797 inline
800 {
801  return ( myPatternEnd - myNextBefore );
802 }
803 
804 
808 template < typename TConstIterator, typename TInteger >
809 inline
812 {
813  return ( myNextAfter - myPatternBegin );
814 }
815 
821 template < typename TConstIterator, typename TInteger >
822 inline
824 {
825  return ( (pos == myPatternBegin) || ( pos == myPatternEnd ) );
826 }
827 
828 
829 
835 template < typename TConstIterator, typename TInteger >
836 inline
838 {
839  return ( (pos - myPatternBegin) == mainPatternLength() - myLeftPatternLength - 1) ;
840 }
841 
847 template < typename TConstIterator, typename TInteger >
848 inline
850 {
851  return ( (pos - myPatternBegin) == mainPatternLength() - myLeftPatternLength ) ;
852 }
853 
854 
858 template < typename TConstIterator, typename TInteger >
859 inline
861 {
862  // If there is no left subpattern, then the DSS is trivial.
863  return ( myLeftPatternLength == 0 );
864 }
865 
866 
867 template < typename TConstIterator, typename TInteger >
868 inline
871 {
872  return myBegin;
873 }
874 
875 template < typename TConstIterator, typename TInteger >
876 inline
879 {
880  return myEnd;
881 }
882 
883 
887 template < typename TConstIterator, typename TInteger >
888 inline
891 {
892  return ConstPointIterator( this, myFirstLetter, myFirstPoint );
893 }
894 
895 
899 template < typename TConstIterator, typename TInteger >
900 inline
903 {
904  ConstPointIterator it ( this, myLastLetter+1, myLastPoint );
905  return ++it;
906 }
907 
908 
909 
910 
914 template < typename TConstIterator, typename TInteger >
915 inline
918 {
919  Integer a,b,mu,omega;
920  getArithmeticalDescription ( a, b, mu, omega);
921  return a;
922 }
923 
927 template < typename TConstIterator, typename TInteger >
928 inline
931 {
932  Integer a,b,mu,omega;
933  getArithmeticalDescription ( a, b, mu, omega);
934  return b;
935 }
936 
937 
938 
942 template < typename TConstIterator, typename TInteger >
943 inline
946 {
947  Integer a,b,mu,omega;
948  getArithmeticalDescription ( a, b, mu, omega );
949  return mu;
950 }
951 
952 
956 template < typename TConstIterator, typename TInteger >
957 inline
960 {
961  Integer a,b,mu,omega;
962  getArithmeticalDescription ( a, b, mu, omega );
963  return omega;
964 }
965 
966 
973 template < typename TConstIterator, typename TInteger >
974 inline
976  Integer &a, Integer &b, Integer &mu, Integer &omega ) const
977 {
978  ConstPointIterator itBegin = pointBegin();
979  while ( itBegin.getIndex() != myPatternBegin )
980  itBegin++;
981  ConstPointIterator itEnd = pointEnd();
982  while ( itEnd.getIndex() != myPatternEnd+1 )
983  itEnd--;
985  Size myRightPatternLenght = mainPatternLength() - myLeftPatternLength;
986  it = itBegin;
987  for (int i=0; i<myRightPatternLenght; i++)
988  it++;
989  Point pb = *itBegin;
990  Point pe = *itEnd;
991  Point po = *it;
992  Vector v = pe - pb;
993  a = v.at(1);
994  b = v.at(0);
995  Integer r1 = a*pb.at(0) - b*pb.at(1);
996  Integer r2 = a*po.at(0) - b*po.at(1);
997  mu = min (r1, r2);
998  omega = ((a>0) ? a : -a) + ((b>0) ? b : -b );
999 }
1000 
1001 
1002 template < typename TConstIterator, typename TInteger >
1003 inline
1005  Point & uf, Point & ul,
1006  Point & lf, Point & ll ) const
1007 {
1008  ConstPointIterator it = pointBegin();
1009  while ( ! isUL ( it.getIndex() ) )
1010  ++it;
1011  uf = *it;
1012 
1013  Vector v = mainPatternVector();
1014  ul = uf + v*myNbRepeat;
1015 
1016  while ( ! previousIsLL ( it.getIndex() ) )
1017  ++it;
1018  lf = ( suffixLength() >= myLeftPatternLength ) ? *it - mainPatternVector() : *it;
1019 
1020  int nbLowerRepeats = ( prefixLength() >= mainPatternLength() - myLeftPatternLength )
1021  ? myNbRepeat : myNbRepeat - 1;
1022  ll = *it + v*nbLowerRepeats;
1023 
1024  if ( getRemainder( uf ) > getRemainder( lf ) )
1025  {
1026  swap ( uf, lf );
1027  swap ( ul, ll );
1028  }
1029 }
1030 
1031 
1032 
1033 
1037 template < typename TConstIterator, typename TInteger >
1038 inline
1041 {
1042  Point uf, ul, lf, ll;
1043  computeLeaningPoints( uf, ul, lf, ll );
1044  return uf;
1045 }
1046 
1047 
1051 template < typename TConstIterator, typename TInteger >
1052 inline
1055 {
1056  Point uf, ul, lf, ll;
1057  computeLeaningPoints( uf, ul, lf, ll );
1058  return ul;
1059 }
1060 
1061 
1065 template < typename TConstIterator, typename TInteger >
1066 inline
1069 {
1070  Point uf, ul, lf, ll;
1071  computeLeaningPoints( uf, ul, lf, ll );
1072  return lf;
1073 }
1074 
1075 
1079 template < typename TConstIterator, typename TInteger >
1080 inline
1083 {
1084  Point uf, ul, lf, ll;
1085  computeLeaningPoints( uf, ul, lf, ll );
1086  return ll;
1087 }
1088 
1089 
1094 template < typename TConstIterator, typename TInteger >
1095 inline
1098 {
1099  return this->myDisplacements( c );
1100 }
1101 
1102 
1103 template < typename TConstIterator, typename TInteger >
1104 inline
1107 {
1108  Integer a,b,mu,omega;
1109  Integer x = aPoint[0];
1110  Integer y = aPoint[1];
1111  getArithmeticalDescription( a, b, mu, omega );
1112  return a*x - b*y;
1113 }
1114 
1115 
1116 // //
1118 
1119 
1120 // ----------------------- Accessors --------------------------------------
1121 
1122 
1127 template < typename TConstIterator, typename TInteger >
1128 inline
1131 {
1132  return myFirstPoint;
1133 }
1134 
1135 
1140 template < typename TConstIterator, typename TInteger >
1141 inline
1144 {
1145  return myLastPoint;
1146 }
1147 
1148 
1165 //template <typename TInteger>
1166 //bool
1167 //CombinatorialDSS<TInteger>::longestChristoffelPrefix(
1168 // Iterator it,
1169 // const OrderedAlphabet & aAlph)
1170 //{
1171 // OrderedAlphabet::Size nb;
1172 // OrderedAlphabet::Size len;
1173 // OrderedAlphabet::Index e = it.getChain()->end().getPosition();
1174 // unsigned int a,b;
1175 // unsigned int lf1, lf2;
1176 // bool cvx = aAlph.duvalPPtoDSS(len, nb, a, b, lf1, lf2,
1177 // it.getChain()->chain, it.getPosition(), e);
1178 //
1179 // len *= nb;
1180 // Vector direction1 = FreemanChainCode::displacement(aAlph.letter(1) - '0');
1181 // Vector direction2 = FreemanChainCode::displacement(aAlph.letter(2) - '0');
1182 // Vector basicMove = ( direction1 * (Integer) a ) + (direction2 * (Integer) b );
1183 // bool trivial = (a == 0 || b == 0);
1184 //
1185 // this->myA = basicMove[1];
1186 // this->myB = basicMove[0];
1187 // this->myNbUpPat = (Integer) nb;
1188 // this->myNbLowPat = (trivial) ? this->myNbUpPat : this->myNbUpPat - 1;
1189 // this->myUf = it.get();
1190 // this->myUl = this->myUf + basicMove*nb;
1191 // this->myLf = (trivial) ?
1192 // this->myUf :
1193 // this->myUf + ( direction1*(Integer)lf1 ) + (direction2*(Integer)lf2 );
1194 // this->myLl = (trivial) ? this->myLf + basicMove*nb :
1195 // this->myLf + basicMove*(nb-1);
1196 // this->myMu = this->myA*this->myUf[0] - this->myB*this->myUf[1];
1197 // this->myOmega = DSS::template Tools<Integer,4>::norm(this->myA,this->myB);
1198 // this->myF = it;
1199 // this->myL = Iterator(*it.getChain(), it.getPosition() + len, this->myUl);
1200 // this->mySteps.clear();
1201 // if (a != 0)
1202 // this->mySteps.push_back(direction1);
1203 // if (b != 0)
1204 // this->mySteps.push_back(direction2);
1205 // return cvx;
1206 //}
1207