2 * This program is free software: you can redistribute it and/or modify
3 * it under the terms of the GNU Lesser General Public License as
4 * published by the Free Software Foundation, either version 3 of the
5 * License, or (at your option) any later version.
7 * This program is distributed in the hope that it will be useful,
8 * but WITHOUT ANY WARRANTY; without even the implied warranty of
9 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10 * GNU General Public License for more details.
12 * You should have received a copy of the GNU General Public License
13 * along with this program. If not, see <http://www.gnu.org/licenses/>.
18 * @file KhalimskySpaceND.ih
19 * @author Jacques-Olivier Lachaud (\c jacques-olivier.lachaud@univ-savoie.fr )
20 * Laboratory of Mathematics (CNRS, UMR 5807), University of Savoie, France
24 * Implementation of inline methods defined in KhalimskySpaceND.h
26 * This file is part of the DGtal library.
30 //////////////////////////////////////////////////////////////////////////////
31 #include <DGtal/io/Color.h>
32 #include <DGtal/kernel/NumberTraits.h>
33 //////////////////////////////////////////////////////////////////////////////
35 ///////////////////////////////////////////////////////////////////////////////
36 // Namescape scope definition of static constants.
37 ///////////////////////////////////////////////////////////////////////////////
39 template < DGtal::Dimension dim, typename TInteger >
42 DGtal::KhalimskySpaceND<dim, TInteger>::dimension;
44 template < DGtal::Dimension dim, typename TInteger >
47 DGtal::KhalimskySpaceND<dim, TInteger>::DIM;
49 template < DGtal::Dimension dim, typename TInteger >
51 typename DGtal::KhalimskySpaceND<dim, TInteger>::Sign
52 DGtal::KhalimskySpaceND<dim, TInteger>::POS;
54 template < DGtal::Dimension dim, typename TInteger >
56 typename DGtal::KhalimskySpaceND<dim, TInteger>::Sign
57 DGtal::KhalimskySpaceND<dim, TInteger>::NEG;
59 ///////////////////////////////////////////////////////////////////////////////
60 // IMPLEMENTATION of inline methods.
61 ///////////////////////////////////////////////////////////////////////////////
63 ///////////////////////////////////////////////////////////////////////////////
65 ///////////////////////////////////////////////////////////////////////////////
66 //-----------------------------------------------------------------------------
67 template < DGtal::Dimension dim, typename TInteger >
69 DGtal::KhalimskyCell< dim, TInteger >::
70 KhalimskyCell( Integer )
74 //-----------------------------------------------------------------------------
75 template < DGtal::Dimension dim, typename TInteger >
77 DGtal::KhalimskyCell< dim, TInteger >::
78 KhalimskyCell( const Point & p )
82 //-----------------------------------------------------------------------------
83 template < DGtal::Dimension dim, typename TInteger >
85 DGtal::KhalimskyCell< dim, TInteger >::
86 KhalimskyCell( const PreCell & aCell )
90 //-----------------------------------------------------------------------------
91 template < DGtal::Dimension dim, typename TInteger >
93 DGtal::KhalimskyCell< dim, TInteger >::
94 operator DGtal::KhalimskyPreCell< dim, TInteger > const& () const
98 //-----------------------------------------------------------------------------
99 template < DGtal::Dimension dim, typename TInteger >
101 DGtal::KhalimskyPreCell< dim, TInteger > const &
102 DGtal::KhalimskyCell< dim, TInteger >::
107 //-----------------------------------------------------------------------------
108 template < DGtal::Dimension dim, typename TInteger >
110 DGtal::KhalimskyCell< dim, TInteger >::
111 operator DGtal::KhalimskyPreCell< dim, TInteger > & ()
115 //-----------------------------------------------------------------------------
116 template < DGtal::Dimension dim, typename TInteger >
119 DGtal::KhalimskyCell< dim, TInteger >::
120 operator==( const KhalimskyCell & other ) const
122 return myPreCell == other.myPreCell;
124 //-----------------------------------------------------------------------------
125 template < DGtal::Dimension dim, typename TInteger >
128 DGtal::KhalimskyCell< dim, TInteger >::
129 operator!=( const KhalimskyCell & other ) const
131 return myPreCell != other.myPreCell;
133 //-----------------------------------------------------------------------------
134 template < DGtal::Dimension dim, typename TInteger >
137 DGtal::KhalimskyCell< dim, TInteger >::
138 operator<( const KhalimskyCell & other ) const
140 return myPreCell < other.myPreCell;
142 //-----------------------------------------------------------------------------
143 template < DGtal::Dimension dim, typename TInteger >
146 DGtal::operator<<( std::ostream & out,
147 const KhalimskyCell< dim, TInteger > & object )
149 out << static_cast< const KhalimskyPreCell<dim, TInteger> & >(object);
153 //------------------------------------------------------------------------------
154 template < DGtal::Dimension dim, typename TInteger >
157 DGtal::KhalimskyCell<dim, TInteger>::
160 return "KhalimskyCell";
163 ///////////////////////////////////////////////////////////////////////////////
164 // SignedKhalimskyCell
165 ///////////////////////////////////////////////////////////////////////////////
166 //-----------------------------------------------------------------------------
167 template < DGtal::Dimension dim, typename TInteger >
169 DGtal::SignedKhalimskyCell< dim, TInteger >::
170 SignedKhalimskyCell( Integer )
174 //-----------------------------------------------------------------------------
175 template < DGtal::Dimension dim, typename TInteger >
177 DGtal::SignedKhalimskyCell< dim, TInteger >::
178 SignedKhalimskyCell( const Point & p, bool positive )
179 : mySPreCell( p, positive )
182 //-----------------------------------------------------------------------------
183 template < DGtal::Dimension dim, typename TInteger >
185 DGtal::SignedKhalimskyCell< dim, TInteger >::
186 SignedKhalimskyCell( const SPreCell & aCell )
187 : mySPreCell( aCell )
190 //-----------------------------------------------------------------------------
191 template < DGtal::Dimension dim, typename TInteger >
193 DGtal::SignedKhalimskyCell< dim, TInteger >::
194 operator DGtal::SignedKhalimskyPreCell< dim, TInteger > const& () const
198 //-----------------------------------------------------------------------------
199 template < DGtal::Dimension dim, typename TInteger >
201 DGtal::SignedKhalimskyPreCell< dim, TInteger > const &
202 DGtal::SignedKhalimskyCell< dim, TInteger >::
207 //-----------------------------------------------------------------------------
208 template < DGtal::Dimension dim, typename TInteger >
210 DGtal::SignedKhalimskyCell< dim, TInteger >::
211 operator DGtal::SignedKhalimskyPreCell< dim, TInteger > & ()
215 //-----------------------------------------------------------------------------
216 template < DGtal::Dimension dim, typename TInteger >
219 DGtal::SignedKhalimskyCell< dim, TInteger >::
220 operator==( const SignedKhalimskyCell & other ) const
222 return mySPreCell == other.mySPreCell;
224 //-----------------------------------------------------------------------------
225 template < DGtal::Dimension dim, typename TInteger >
228 DGtal::SignedKhalimskyCell< dim, TInteger >::
229 operator!=( const SignedKhalimskyCell & other ) const
231 return mySPreCell != other.mySPreCell;
233 //-----------------------------------------------------------------------------
234 template < DGtal::Dimension dim, typename TInteger >
237 DGtal::SignedKhalimskyCell< dim, TInteger >::
238 operator<( const SignedKhalimskyCell & other ) const
240 return mySPreCell < other.mySPreCell;
242 //-----------------------------------------------------------------------------
243 template < DGtal::Dimension dim,
247 DGtal::operator<<( std::ostream & out,
248 const SignedKhalimskyCell< dim, TInteger > & object )
250 out << static_cast< const SignedKhalimskyPreCell<dim, TInteger> & >(object);
254 //------------------------------------------------------------------------------
255 template < DGtal::Dimension dim, typename TInteger >
258 DGtal::SignedKhalimskyCell<dim, TInteger>::
261 return "SignedKhalimskyCell";
264 ///////////////////////////////////////////////////////////////////////////////
265 // KhalimskySpaceNDHelper
266 ///////////////////////////////////////////////////////////////////////////////
271 DGtal::Dimension dim,
274 class KhalimskySpaceNDHelper< KhalimskySpaceND< dim, TInteger > >
278 using KhalimskySpace = KhalimskySpaceND< dim, TInteger >;
279 using Point = PointVector< dim, TInteger >;
280 using Cell = KhalimskyCell< dim, TInteger >;
281 using SCell = SignedKhalimskyCell< dim, TInteger >;
283 /// Returns derived mutable instance
284 KhalimskySpace& derived()
286 return *static_cast<KhalimskySpace*>(this);
289 /// Returns derived constant instance
290 KhalimskySpace const & derived() const
292 return *static_cast<KhalimskySpace const*>(this);
299 /// @return true is the specified dimension is periodic
301 bool isDimensionPeriodicHelper( DGtal::Dimension d ) const
303 return derived().myClosure[ d ] == KhalimskySpace::PERIODIC;
306 /// @return true is there is at least one periodic dimension.
308 bool isAnyDimensionPeriodicHelper() const
310 return myIsAnyDimensionPeriodic;
313 /** Modifies a khalimsky coordinate according to the dimension periodicity.
314 * @param[in,out] aKCoord the coordinate to modify.
315 * @param d the coordinate dimension.
318 void updateKCoordHelper( typename Point::Coordinate & aKCoord, DGtal::Dimension d ) const
320 if ( isDimensionPeriodicHelper( d ) )
322 aKCoord = ( aKCoord - derived().myCellLower.myPreCell.coordinates[ d ] ) % myCellExtent[ d ];
323 aKCoord += ( ( aKCoord < 0 ) ?
324 derived().myCellUpper.myPreCell.coordinates[ d ] + 1
325 : derived().myCellLower.myPreCell.coordinates[ d ]
330 /** Returns a given khalimsky coordinate modified according to the dimension periodicity.
331 * @param[in] aKCoord the coordinate to modify.
332 * @param d the coordinate dimension.
333 * @returns the modified coordinate.
336 typename Point::Coordinate returnKCoordHelper( typename Point::Coordinate aKCoord, DGtal::Dimension d ) const
338 updateKCoordHelper( aKCoord, d );
342 /** Modifies khalimsky coordinates of a point according to the dimension periodicity.
343 * @param[in,out] aKCoords the khalimksy coordinates.
346 void updateKCoordsHelper( Point & aKCoords ) const
348 if ( isAnyDimensionPeriodicHelper() )
350 for ( DGtal::Dimension i = 0; i < dim; ++i )
351 updateKCoordHelper( aKCoords[ i ], i );
355 /** Returns given khalimsky coordinates of a point modified according to the dimension periodicity.
356 * @param[in] aKCoords the khalimksy coordinates.
359 Point returnKCoordsHelper( Point aKCoords ) const
361 updateKCoordsHelper( aKCoords );
365 /** Modifies a cell's khalimsky coordinate according to the dimension periodicity.
366 * @param[in,out] aCell an unsigned cell.
367 * @param d the coordinate dimension.
370 void updateCellHelper( Cell & aCell, DGtal::Dimension d ) const
372 updateKCoordHelper( aCell.myPreCell.coordinates[ d ], d );
375 /** Modifies a cell's khalimsky coordinates according to the dimension periodicity.
376 * @param[in,out] aCell an unsigned cell.
379 void updateCellHelper( Cell & aCell ) const
381 updateKCoordsHelper( aCell.myPreCell.coordinates );
384 /** Modifies a cell's khalimsky coordinate according to the dimension periodicity.
385 * @param[in,out] aCell a signed cell.
386 * @param d the coordinate dimension.
389 void updateSCellHelper( SCell & aCell, DGtal::Dimension d ) const
391 updateKCoordHelper( aCell.mySPreCell.coordinates[ d ], d );
394 /** Modifies a cell's khalimsky coordinates according to the dimension periodicity.
395 * @param[in,out] aCell a signed cell.
398 void updateSCellHelper( SCell & aCell ) const
400 updateKCoordsHelper( aCell.mySPreCell.coordinates );
407 myIsAnyDimensionPeriodic = false;
408 for ( DGtal::Dimension i = 0; i < dim; ++i )
410 myIsAnyDimensionPeriodic |= isDimensionPeriodicHelper( i );
411 myCellExtent[ i ] = derived().myCellUpper.myPreCell.coordinates[ i ] - derived().myCellLower.myPreCell.coordinates[ i ] + 1;
420 Point myCellExtent; ///< Extent between the extremal cells.
421 bool myIsAnyDimensionPeriodic; ///< true if there is at least one periodic dimension.
426 ///////////////////////////////////////////////////////////////////////////////
428 ///////////////////////////////////////////////////////////////////////////////
429 ///////////////////////////////////////////////////////////////////////////////
430 // ----------------------- Standard services ------------------------------
431 //-----------------------------------------------------------------------------
432 template < DGtal::Dimension dim, typename TInteger>
434 DGtal::KhalimskySpaceND< dim, TInteger>::
438 //-----------------------------------------------------------------------------
439 template < DGtal::Dimension dim, typename TInteger>
441 DGtal::KhalimskySpaceND< dim, TInteger>::
445 for ( DGtal::Dimension i = 0; i < dimension; ++i )
447 low[ i ] = NumberTraits< Integer >::min() / 2 + 1;
448 high[ i ] = NumberTraits< Integer >::max() / 2 - 1;
450 init( low, high, true );
452 //-----------------------------------------------------------------------------
453 template < DGtal::Dimension dim, typename TInteger>
456 DGtal::KhalimskySpaceND< dim, TInteger>::
457 init( const Point & lower,
461 std::array<Closure, dimension> closure;
462 for ( DGtal::Dimension i = 0; i < dimension; ++i )
463 closure[ i ] = isClosed ? CLOSED : OPEN;
465 return init( lower, upper, closure );
467 //-----------------------------------------------------------------------------
468 template < DGtal::Dimension dim, typename TInteger>
471 DGtal::KhalimskySpaceND< dim, TInteger>::
472 init( const Point & lower,
476 std::array<Closure, dimension> dimClosure;
477 dimClosure.fill( closure );
479 return init( lower, upper, dimClosure );
482 //-----------------------------------------------------------------------------
483 template < DGtal::Dimension dim, typename TInteger>
486 DGtal::KhalimskySpaceND< dim, TInteger>::
487 init( const Point & lower,
489 const std::array<Closure, dim> & closure )
495 if ( NumberTraits< Integer >::isBounded() == BOUNDED )
497 for ( DGtal::Dimension i = 0; i < dimension; ++i )
499 if ( ( lower[ i ] <= ( NumberTraits< Integer >::min() / 2 ) )
500 || ( upper[ i ] >= ( NumberTraits< Integer >::max() / 2 ) ) )
505 for ( DGtal::Dimension i = 0; i < dimension; ++i )
507 PreCellularGridSpace::uSetKCoord( myCellLower.myPreCell, i, ( lower[ i ] * 2 ) + ( closure[ i ] != OPEN ? 0 : 1 ) );
508 PreCellularGridSpace::uSetKCoord( myCellUpper.myPreCell, i, ( upper[ i ] * 2 ) + ( closure[ i ] == CLOSED ? 2 : 1 ) );
512 return this->initHelper();
514 //-----------------------------------------------------------------------------
515 template < DGtal::Dimension dim, typename TInteger>
517 typename DGtal::KhalimskySpaceND< dim, TInteger>::Size
518 DGtal::KhalimskySpaceND< dim, TInteger>::
519 size( DGtal::Dimension k ) const
521 ASSERT( k < dimension );
522 return myUpper[ k ] + NumberTraits<Integer>::ONE - myLower[ k ];
524 //-----------------------------------------------------------------------------
525 template < DGtal::Dimension dim, typename TInteger>
528 DGtal::KhalimskySpaceND< dim, TInteger>::
529 min( DGtal::Dimension k ) const
533 //-----------------------------------------------------------------------------
534 template < DGtal::Dimension dim, typename TInteger>
537 DGtal::KhalimskySpaceND< dim, TInteger>::
538 max( DGtal::Dimension k ) const
542 //-----------------------------------------------------------------------------
543 template < DGtal::Dimension dim, typename TInteger>
545 const typename DGtal::KhalimskySpaceND< dim, TInteger>::Point &
546 DGtal::KhalimskySpaceND< dim, TInteger>::
551 //-----------------------------------------------------------------------------
552 template < DGtal::Dimension dim, typename TInteger>
554 const typename DGtal::KhalimskySpaceND< dim, TInteger>::Point &
555 DGtal::KhalimskySpaceND< dim, TInteger>::
560 //-----------------------------------------------------------------------------
561 template < DGtal::Dimension dim, typename TInteger>
563 const typename DGtal::KhalimskySpaceND< dim, TInteger>::Cell &
564 DGtal::KhalimskySpaceND< dim, TInteger>::
569 //-----------------------------------------------------------------------------
570 template < DGtal::Dimension dim, typename TInteger>
572 const typename DGtal::KhalimskySpaceND< dim, TInteger>::Cell &
573 DGtal::KhalimskySpaceND< dim, TInteger>::
578 //-----------------------------------------------------------------------------
579 template < DGtal::Dimension dim, typename TInteger>
582 DGtal::KhalimskySpaceND< dim, TInteger>::
583 uIsValid( const PreCell & p, Dimension k ) const
585 return cIsValid( p.coordinates, k );
587 //-----------------------------------------------------------------------------
588 template < DGtal::Dimension dim, typename TInteger>
591 DGtal::KhalimskySpaceND< dim, TInteger>::
592 uIsValid( const PreCell & p ) const
594 return cIsValid( p.coordinates );
596 //-----------------------------------------------------------------------------
597 template < DGtal::Dimension dim, typename TInteger>
600 DGtal::KhalimskySpaceND< dim, TInteger>::
601 cIsValid( const Point & p, Dimension k ) const
603 return p[ k ] <= PreCellularGridSpace::uKCoord( myCellUpper, k )
604 && p[ k ] >= PreCellularGridSpace::uKCoord( myCellLower, k );
606 //-----------------------------------------------------------------------------
607 template < DGtal::Dimension dim, typename TInteger>
610 DGtal::KhalimskySpaceND< dim, TInteger>::
611 cIsValid( const Point & p ) const
613 for ( Dimension k = 0; k < DIM; ++ k )
614 if ( ! cIsValid( p, k ) )
619 //-----------------------------------------------------------------------------
620 template < DGtal::Dimension dim, typename TInteger>
623 DGtal::KhalimskySpaceND< dim, TInteger>::
624 sIsValid( const SPreCell & p, Dimension k ) const
626 return cIsValid( p.coordinates, k );
628 //-----------------------------------------------------------------------------
629 template < DGtal::Dimension dim, typename TInteger>
632 DGtal::KhalimskySpaceND< dim, TInteger>::
633 sIsValid( const SPreCell & p ) const
635 return cIsValid( p.coordinates );
637 //-----------------------------------------------------------------------------
638 template < DGtal::Dimension dim, typename TInteger>
641 DGtal::KhalimskySpaceND< dim, TInteger>::
642 isSpaceClosed() const
644 for ( Dimension i = 0; i < dimension; ++i )
645 if ( myClosure[ i ] == OPEN )
650 //-----------------------------------------------------------------------------
651 template < DGtal::Dimension dim, typename TInteger>
654 DGtal::KhalimskySpaceND< dim, TInteger>::
655 isSpaceClosed( Dimension k ) const
657 return myClosure[ k ] != OPEN;
659 //-----------------------------------------------------------------------------
660 template < DGtal::Dimension dim, typename TInteger>
663 DGtal::KhalimskySpaceND< dim, TInteger>::
664 isSpacePeriodic() const
666 for ( Dimension i = 0; i < dimension; ++i )
667 if ( myClosure[ i ] != PERIODIC )
672 //-----------------------------------------------------------------------------
673 template < DGtal::Dimension dim, typename TInteger>
676 DGtal::KhalimskySpaceND< dim, TInteger>::
677 isSpacePeriodic( Dimension k ) const
679 return myClosure[ k ] == PERIODIC;
681 //-----------------------------------------------------------------------------
682 template < DGtal::Dimension dim, typename TInteger>
685 DGtal::KhalimskySpaceND< dim, TInteger>::
686 isAnyDimensionPeriodic() const
688 return this->isAnyDimensionPeriodicHelper();
690 //-----------------------------------------------------------------------------
691 template < DGtal::Dimension dim, typename TInteger>
693 typename DGtal::KhalimskySpaceND< dim, TInteger>::Closure
694 DGtal::KhalimskySpaceND< dim, TInteger>::
695 getClosure(Dimension k) const
699 //-----------------------------------------------------------------------------
700 template < DGtal::Dimension dim, typename TInteger>
702 typename DGtal::KhalimskySpaceND< dim, TInteger>::Cell
703 DGtal::KhalimskySpaceND< dim, TInteger>::
704 uCell( const PreCell & c ) const
706 return uCell( c.coordinates );
708 //-----------------------------------------------------------------------------
709 template < DGtal::Dimension dim, typename TInteger>
711 typename DGtal::KhalimskySpaceND< dim, TInteger>::Cell
712 DGtal::KhalimskySpaceND< dim, TInteger>::
713 uCell( const Point & kp ) const
715 ASSERT( cIsInside( kp ) );
716 return Cell( this->returnKCoordsHelper( kp ) );
718 //-----------------------------------------------------------------------------
719 template < DGtal::Dimension dim, typename TInteger>
721 typename DGtal::KhalimskySpaceND< dim, TInteger>::Cell
722 DGtal::KhalimskySpaceND< dim, TInteger>::
723 uCell( Point p, const PreCell & c ) const
725 return uCell( PreCellularGridSpace::uCell( p, c ) );
727 //-----------------------------------------------------------------------------
728 template < DGtal::Dimension dim, typename TInteger>
730 typename DGtal::KhalimskySpaceND< dim, TInteger>::SCell
731 DGtal::KhalimskySpaceND< dim, TInteger>::
732 sCell( const SPreCell & c ) const
734 return sCell( c.coordinates, c.positive ? POS : NEG );
736 //-----------------------------------------------------------------------------
737 template < DGtal::Dimension dim, typename TInteger>
739 typename DGtal::KhalimskySpaceND< dim, TInteger>::SCell
740 DGtal::KhalimskySpaceND< dim, TInteger>::
741 sCell( const Point & kp, Sign sign ) const
743 ASSERT( cIsInside( kp ) );
744 return SCell( this->returnKCoordsHelper( kp ), sign == POS );
746 //-----------------------------------------------------------------------------
747 template < DGtal::Dimension dim, typename TInteger>
749 typename DGtal::KhalimskySpaceND< dim, TInteger>::SCell
750 DGtal::KhalimskySpaceND< dim, TInteger>::
751 sCell( Point p, const SPreCell & c ) const
753 return sCell( PreCellularGridSpace::sCell( p, c ) );
755 //-----------------------------------------------------------------------------
756 template < DGtal::Dimension dim, typename TInteger>
758 typename DGtal::KhalimskySpaceND< dim, TInteger>::Cell
759 DGtal::KhalimskySpaceND< dim, TInteger>::
760 uSpel( Point p ) const
762 return uCell( PreCellularGridSpace::uSpel( p ) );
764 //-----------------------------------------------------------------------------
765 template < DGtal::Dimension dim, typename TInteger>
767 typename DGtal::KhalimskySpaceND< dim, TInteger>::SCell
768 DGtal::KhalimskySpaceND< dim, TInteger>::
769 sSpel( Point p, Sign sign ) const
771 return sCell( PreCellularGridSpace::sSpel( p, sign ) );
773 //-----------------------------------------------------------------------------
774 template < DGtal::Dimension dim, typename TInteger>
776 typename DGtal::KhalimskySpaceND< dim, TInteger>::Cell
777 DGtal::KhalimskySpaceND< dim, TInteger>::
778 uPointel( Point p ) const
780 return uCell( PreCellularGridSpace::uPointel( p ) );
782 //-----------------------------------------------------------------------------
783 template < DGtal::Dimension dim, typename TInteger>
785 typename DGtal::KhalimskySpaceND< dim, TInteger>::SCell
786 DGtal::KhalimskySpaceND< dim, TInteger>::
787 sPointel( Point p, Sign sign ) const
789 return sCell( PreCellularGridSpace::sPointel( p, sign ) );
791 //-----------------------------------------------------------------------------
792 ///////////////////////////////////////////////////////////////////////////////
793 //-----------------------------------------------------------------------------
794 template < DGtal::Dimension dim, typename TInteger>
796 typename DGtal::KhalimskySpaceND< dim, TInteger>::Integer
797 DGtal::KhalimskySpaceND< dim, TInteger>::
798 uKCoord( const Cell & c, DGtal::Dimension k ) const
800 ASSERT( uIsValid(c) );
801 return PreCellularGridSpace::uKCoord( c, k );
803 //-----------------------------------------------------------------------------
804 template < DGtal::Dimension dim, typename TInteger>
806 typename DGtal::KhalimskySpaceND< dim, TInteger>::Integer
807 DGtal::KhalimskySpaceND< dim, TInteger>::
808 uCoord( const Cell & c, DGtal::Dimension k ) const
810 ASSERT( uIsValid(c) );
811 return PreCellularGridSpace::uCoord( c, k );
813 //-----------------------------------------------------------------------------
814 template < DGtal::Dimension dim, typename TInteger>
816 typename DGtal::KhalimskySpaceND< dim, TInteger>::Point const &
817 DGtal::KhalimskySpaceND< dim, TInteger>::
818 uKCoords( const Cell & c ) const
820 ASSERT( uIsValid(c) );
821 return PreCellularGridSpace::uKCoords( c );
823 //-----------------------------------------------------------------------------
824 template < DGtal::Dimension dim, typename TInteger>
826 typename DGtal::KhalimskySpaceND< dim, TInteger>::Point
827 DGtal::KhalimskySpaceND< dim, TInteger>::
828 uCoords( const Cell & c ) const
830 ASSERT( uIsValid(c) );
831 return PreCellularGridSpace::uCoords( c );
833 //-----------------------------------------------------------------------------
834 template < DGtal::Dimension dim, typename TInteger>
836 typename DGtal::KhalimskySpaceND< dim, TInteger>::Integer
837 DGtal::KhalimskySpaceND< dim, TInteger>::
838 sKCoord( const SCell & c, DGtal::Dimension k ) const
840 ASSERT( sIsValid(c) );
841 return PreCellularGridSpace::sKCoord( c, k );
843 //-----------------------------------------------------------------------------
844 template < DGtal::Dimension dim, typename TInteger>
846 typename DGtal::KhalimskySpaceND< dim, TInteger>::Integer
847 DGtal::KhalimskySpaceND< dim, TInteger>::
848 sCoord( const SCell & c, DGtal::Dimension k ) const
850 ASSERT( sIsValid(c) );
851 return PreCellularGridSpace::sCoord( c, k );
853 //-----------------------------------------------------------------------------
854 template < DGtal::Dimension dim, typename TInteger>
856 typename DGtal::KhalimskySpaceND< dim, TInteger>::Point const &
857 DGtal::KhalimskySpaceND< dim, TInteger>::
858 sKCoords( const SCell & c ) const
860 ASSERT( sIsValid(c) );
861 return PreCellularGridSpace::sKCoords( c );
863 //-----------------------------------------------------------------------------
864 template < DGtal::Dimension dim, typename TInteger>
866 typename DGtal::KhalimskySpaceND< dim, TInteger>::Point
867 DGtal::KhalimskySpaceND< dim, TInteger>::
868 sCoords( const SCell & c ) const
870 ASSERT( sIsValid(c) );
871 return PreCellularGridSpace::sCoords( c );
873 //-----------------------------------------------------------------------------
874 template < DGtal::Dimension dim, typename TInteger>
876 typename DGtal::KhalimskySpaceND< dim, TInteger>::Sign
877 DGtal::KhalimskySpaceND< dim, TInteger>::
878 sSign( const SCell & c ) const
880 ASSERT( sIsValid(c) );
881 return PreCellularGridSpace::sSign( c );
883 //-----------------------------------------------------------------------------
884 template < DGtal::Dimension dim, typename TInteger>
886 typename DGtal::KhalimskySpaceND< dim, TInteger>::SCell
887 DGtal::KhalimskySpaceND< dim, TInteger>::
888 signs( const Cell & p, Sign s ) const
890 return sCell( PreCellularGridSpace::signs( p, s ) );
892 //-----------------------------------------------------------------------------
893 template < DGtal::Dimension dim, typename TInteger>
895 typename DGtal::KhalimskySpaceND< dim, TInteger>::Cell
896 DGtal::KhalimskySpaceND< dim, TInteger>::
897 unsigns( const SCell & p ) const
899 return uCell( PreCellularGridSpace::unsigns( p ) );
901 //-----------------------------------------------------------------------------
902 template < DGtal::Dimension dim, typename TInteger>
904 typename DGtal::KhalimskySpaceND< dim, TInteger>::SCell
905 DGtal::KhalimskySpaceND< dim, TInteger>::
906 sOpp( const SCell & p ) const
908 return sCell( PreCellularGridSpace::sOpp( p ) );
910 //-----------------------------------------------------------------------------
911 template < DGtal::Dimension dim, typename TInteger>
914 DGtal::KhalimskySpaceND< dim, TInteger>::
915 uSetKCoord( Cell & c, DGtal::Dimension k, Integer i ) const
917 PreCellularGridSpace::uSetKCoord( c.myPreCell, k, i );
918 this->updateCellHelper( c, k );
919 ASSERT( uIsValid(c) );
921 //-----------------------------------------------------------------------------
922 template < DGtal::Dimension dim, typename TInteger>
925 DGtal::KhalimskySpaceND< dim, TInteger>::
926 sSetKCoord( SCell & c, DGtal::Dimension k, Integer i ) const
928 PreCellularGridSpace::sSetKCoord( c.mySPreCell, k, i );
929 this->updateSCellHelper( c, k );
930 ASSERT( sIsValid(c) );
932 //-----------------------------------------------------------------------------
933 template < DGtal::Dimension dim, typename TInteger>
936 DGtal::KhalimskySpaceND< dim, TInteger>::
937 uSetCoord( Cell & c, DGtal::Dimension k, Integer i ) const
939 PreCellularGridSpace::uSetCoord( c.myPreCell, k, i );
940 this->updateCellHelper( c, k );
941 ASSERT( uIsValid(c) );
943 //-----------------------------------------------------------------------------
944 template < DGtal::Dimension dim, typename TInteger>
947 DGtal::KhalimskySpaceND< dim, TInteger>::
948 sSetCoord( SCell & c, DGtal::Dimension k, Integer i ) const
950 PreCellularGridSpace::sSetCoord( c.mySPreCell, k, i );
951 this->updateSCellHelper( c, k );
952 ASSERT( sIsValid(c) );
954 //-----------------------------------------------------------------------------
955 template < DGtal::Dimension dim, typename TInteger>
958 DGtal::KhalimskySpaceND< dim, TInteger>::
959 uSetKCoords( Cell & c, const Point & kp ) const
961 PreCellularGridSpace::uSetKCoords( c.myPreCell, kp );
962 this->updateCellHelper( c );
963 ASSERT( uIsValid(c) );
965 //-----------------------------------------------------------------------------
966 template < DGtal::Dimension dim, typename TInteger>
969 DGtal::KhalimskySpaceND< dim, TInteger>::
970 sSetKCoords( SCell & c, const Point & kp ) const
972 PreCellularGridSpace::sSetKCoords( c.mySPreCell, kp );
973 this->updateSCellHelper( c );
974 ASSERT( sIsValid(c) );
976 //-----------------------------------------------------------------------------
977 template < DGtal::Dimension dim, typename TInteger>
980 DGtal::KhalimskySpaceND< dim, TInteger>::
981 uSetCoords( Cell & c, const Point & p ) const
983 PreCellularGridSpace::uSetCoords( c.myPreCell, p );
984 this->updateCellHelper( c );
985 ASSERT( uIsValid(c) );
987 //-----------------------------------------------------------------------------
988 template < DGtal::Dimension dim, typename TInteger>
991 DGtal::KhalimskySpaceND< dim, TInteger>::
992 sSetCoords( SCell & c, const Point & p ) const
994 PreCellularGridSpace::sSetCoords( c.mySPreCell, p );
995 this->updateSCellHelper( c );
996 ASSERT( sIsValid(c) );
998 //-----------------------------------------------------------------------------
999 template < DGtal::Dimension dim, typename TInteger>
1002 DGtal::KhalimskySpaceND< dim, TInteger>::
1003 sSetSign( SCell & c, Sign s ) const
1005 PreCellularGridSpace::sSetSign( c.mySPreCell, s );
1007 //-----------------------------------------------------------------------------
1008 // ------------------------- Cell topology services -----------------------
1009 //-----------------------------------------------------------------------------
1010 template < DGtal::Dimension dim, typename TInteger>
1013 DGtal::KhalimskySpaceND< dim, TInteger>::
1014 uTopology( const Cell & p ) const
1016 return PreCellularGridSpace::uTopology( p );
1018 //-----------------------------------------------------------------------------
1019 template < DGtal::Dimension dim, typename TInteger>
1022 DGtal::KhalimskySpaceND< dim, TInteger>::
1023 sTopology( const SCell & p ) const
1025 return PreCellularGridSpace::sTopology( p );
1027 //-----------------------------------------------------------------------------
1028 template < DGtal::Dimension dim, typename TInteger>
1031 DGtal::KhalimskySpaceND< dim, TInteger>::
1032 uDim( const Cell & p ) const
1034 return PreCellularGridSpace::uDim( p );
1036 //-----------------------------------------------------------------------------
1037 template < DGtal::Dimension dim, typename TInteger>
1040 DGtal::KhalimskySpaceND< dim, TInteger>::
1041 sDim( const SCell & p ) const
1043 return PreCellularGridSpace::sDim( p );
1045 //-----------------------------------------------------------------------------
1046 template < DGtal::Dimension dim, typename TInteger>
1049 DGtal::KhalimskySpaceND< dim, TInteger>::
1050 uIsSurfel( const Cell & b ) const
1052 return PreCellularGridSpace::uIsSurfel( b );
1054 //-----------------------------------------------------------------------------
1055 template < DGtal::Dimension dim, typename TInteger>
1058 DGtal::KhalimskySpaceND< dim, TInteger>::
1059 sIsSurfel( const SCell & b ) const
1061 return PreCellularGridSpace::sIsSurfel( b );
1063 //-----------------------------------------------------------------------------
1064 template < DGtal::Dimension dim, typename TInteger>
1067 DGtal::KhalimskySpaceND< dim, TInteger>::
1068 uIsOpen( const Cell & p, DGtal::Dimension k ) const
1070 return PreCellularGridSpace::uIsOpen( p, k );
1072 //-----------------------------------------------------------------------------
1073 template < DGtal::Dimension dim, typename TInteger>
1076 DGtal::KhalimskySpaceND< dim, TInteger>::
1077 sIsOpen( const SCell & p, DGtal::Dimension k ) const
1079 return PreCellularGridSpace::sIsOpen( p, k );
1082 //-----------------------------------------------------------------------------
1083 ///////////////////////////////////////////////////////////////////////////////
1084 //-----------------------------------------------------------------------------
1085 template < DGtal::Dimension dim, typename TInteger>
1087 typename DGtal::KhalimskySpaceND< dim, TInteger>::DirIterator
1088 DGtal::KhalimskySpaceND< dim, TInteger>::
1089 uDirs( const Cell & p ) const
1091 return PreCellularGridSpace::uDirs( p );
1093 //-----------------------------------------------------------------------------
1094 template < DGtal::Dimension dim, typename TInteger>
1096 typename DGtal::KhalimskySpaceND< dim, TInteger>::DirIterator
1097 DGtal::KhalimskySpaceND< dim, TInteger>::
1098 sDirs( const SCell & p ) const
1100 return PreCellularGridSpace::sDirs( p );
1102 //-----------------------------------------------------------------------------
1103 template < DGtal::Dimension dim, typename TInteger>
1105 typename DGtal::KhalimskySpaceND< dim, TInteger>::DirIterator
1106 DGtal::KhalimskySpaceND< dim, TInteger>::
1107 uOrthDirs( const Cell & p ) const
1109 return PreCellularGridSpace::uOrthDirs( p );
1111 //-----------------------------------------------------------------------------
1112 template < DGtal::Dimension dim, typename TInteger>
1114 typename DGtal::KhalimskySpaceND< dim, TInteger>::DirIterator
1115 DGtal::KhalimskySpaceND< dim, TInteger>::
1116 sOrthDirs( const SCell & p ) const
1118 return PreCellularGridSpace::sOrthDirs( p );
1120 //-----------------------------------------------------------------------------
1121 template < DGtal::Dimension dim, typename TInteger>
1124 DGtal::KhalimskySpaceND< dim, TInteger>::
1125 uOrthDir( const Cell & s ) const
1127 return PreCellularGridSpace::uOrthDir( s );
1129 //-----------------------------------------------------------------------------
1130 template < DGtal::Dimension dim, typename TInteger>
1133 DGtal::KhalimskySpaceND< dim, TInteger>::
1134 sOrthDir( const SCell & s ) const
1136 return PreCellularGridSpace::sOrthDir( s );
1138 //-----------------------------------------------------------------------------
1139 ///////////////////////////////////////////////////////////////////////////////
1140 //-----------------------------------------------------------------------------
1141 //-----------------------------------------------------------------------------
1142 template < DGtal::Dimension dim, typename TInteger>
1144 typename DGtal::KhalimskySpaceND< dim, TInteger>::Integer
1145 DGtal::KhalimskySpaceND< dim, TInteger>::
1146 uFirst( const PreCell & p, DGtal::Dimension k ) const
1150 return myClosure[ k ] == OPEN ?
1151 2 * myLower[ k ] + ( NumberTraits<Integer>::odd( p.coordinates[ k ] ) ? 1 : 2 )
1152 : 2 * myLower[ k ] + ( NumberTraits<Integer>::odd( p.coordinates[ k ] ) ? 1 : 0 );
1154 //-----------------------------------------------------------------------------
1155 template < DGtal::Dimension dim, typename TInteger>
1157 typename DGtal::KhalimskySpaceND< dim, TInteger>::Cell
1158 DGtal::KhalimskySpaceND< dim, TInteger>::
1159 uFirst( const PreCell & p ) const
1162 for ( Dimension k = 0; k < dimension; ++k )
1163 PreCellularGridSpace::uSetKCoord( cell.myPreCell, k, uFirst( p, k ) );
1167 //-----------------------------------------------------------------------------
1168 template < DGtal::Dimension dim, typename TInteger>
1170 typename DGtal::KhalimskySpaceND< dim, TInteger>::Integer
1171 DGtal::KhalimskySpaceND< dim, TInteger>::
1172 uLast( const PreCell & p, DGtal::Dimension k ) const
1176 return myClosure[ k ] == CLOSED ?
1177 2 * myUpper[ k ] + ( NumberTraits<Integer>::odd( p.coordinates[ k ] ) ? 1 : 2 )
1178 : 2 * myUpper[ k ] + ( NumberTraits<Integer>::odd( p.coordinates[ k ] ) ? 1 : 0 );
1180 //-----------------------------------------------------------------------------
1181 template < DGtal::Dimension dim, typename TInteger>
1183 typename DGtal::KhalimskySpaceND< dim, TInteger>::Cell
1184 DGtal::KhalimskySpaceND< dim, TInteger>::
1185 uLast( const PreCell & p ) const
1188 for ( Dimension k = 0; k < dimension; ++k )
1189 PreCellularGridSpace::uSetKCoord( cell.myPreCell, k, uLast( p, k ) );
1193 //-----------------------------------------------------------------------------
1194 template < DGtal::Dimension dim, typename TInteger>
1196 typename DGtal::KhalimskySpaceND< dim, TInteger>::Cell
1197 DGtal::KhalimskySpaceND< dim, TInteger>::
1198 uGetIncr( const Cell & p, DGtal::Dimension k ) const
1200 Cell cell( PreCellularGridSpace::uGetIncr( p, k ) );
1201 this->updateCellHelper( cell, k );
1202 ASSERT( uIsValid(cell) );
1205 //-----------------------------------------------------------------------------
1206 template < DGtal::Dimension dim, typename TInteger>
1209 DGtal::KhalimskySpaceND< dim, TInteger>::
1210 uIsMax( const Cell & p, DGtal::Dimension k ) const
1213 ASSERT( uIsInside(p) );
1215 ! this->isDimensionPeriodicHelper( k )
1216 && PreCellularGridSpace::uKCoord( p, k ) >= uLast( p, k );
1218 //-----------------------------------------------------------------------------
1219 template < DGtal::Dimension dim, typename TInteger>
1222 DGtal::KhalimskySpaceND< dim, TInteger>::
1223 uIsInside( const PreCell & p, DGtal::Dimension k ) const
1225 return cIsInside( p.coordinates, k );
1227 //-----------------------------------------------------------------------------
1228 template < DGtal::Dimension dim, typename TInteger>
1231 DGtal::KhalimskySpaceND< dim, TInteger>::
1232 uIsInside( const PreCell & p ) const
1234 return cIsInside( p.coordinates );
1236 //-----------------------------------------------------------------------------
1237 template < DGtal::Dimension dim, typename TInteger>
1240 DGtal::KhalimskySpaceND< dim, TInteger>::
1241 cIsInside( const Point & p, DGtal::Dimension k ) const
1244 return this->isDimensionPeriodicHelper( k )
1245 || cIsValid( p, k );
1247 //-----------------------------------------------------------------------------
1248 template < DGtal::Dimension dim, typename TInteger>
1251 DGtal::KhalimskySpaceND< dim, TInteger>::
1252 cIsInside( const Point & p ) const
1254 for ( Dimension k = 0; k < DIM; ++k )
1255 if ( ! cIsInside( p, k ) )
1260 //-----------------------------------------------------------------------------
1261 template < DGtal::Dimension dim, typename TInteger>
1263 typename DGtal::KhalimskySpaceND< dim, TInteger>::Cell
1264 DGtal::KhalimskySpaceND< dim, TInteger>::
1265 uGetMax( Cell p, DGtal::Dimension k ) const
1267 PreCellularGridSpace::uSetKCoord( p.myPreCell, k, uLast( p, k ) );
1268 ASSERT( uIsValid( p ) );
1271 //-----------------------------------------------------------------------------
1272 template < DGtal::Dimension dim, typename TInteger>
1274 typename DGtal::KhalimskySpaceND< dim, TInteger>::Cell
1275 DGtal::KhalimskySpaceND< dim, TInteger>::
1276 uGetDecr( const Cell & p, DGtal::Dimension k ) const
1278 Cell cell( PreCellularGridSpace::uGetDecr( p, k ) );
1279 this->updateCellHelper( cell, k );
1280 ASSERT( uIsValid( cell ) );
1283 //-----------------------------------------------------------------------------
1284 template < DGtal::Dimension dim, typename TInteger>
1287 DGtal::KhalimskySpaceND< dim, TInteger>::
1288 uIsMin( const Cell & p, DGtal::Dimension k ) const
1290 ASSERT( uIsInside(p) );
1292 ! this->isDimensionPeriodicHelper( k )
1293 && PreCellularGridSpace::uKCoord( p, k ) <= uFirst( p, k );
1295 //-----------------------------------------------------------------------------
1296 template < DGtal::Dimension dim, typename TInteger>
1298 typename DGtal::KhalimskySpaceND< dim, TInteger>::Cell
1299 DGtal::KhalimskySpaceND< dim, TInteger>::
1300 uGetMin( Cell p, DGtal::Dimension k ) const
1302 PreCellularGridSpace::uSetKCoord( p.myPreCell, k, uFirst( p, k ) );
1303 ASSERT( uIsValid(p) );
1306 //-----------------------------------------------------------------------------
1307 template < DGtal::Dimension dim, typename TInteger>
1309 typename DGtal::KhalimskySpaceND< dim, TInteger>::Cell
1310 DGtal::KhalimskySpaceND< dim, TInteger>::
1311 uGetAdd( const Cell & p, DGtal::Dimension k, Integer x ) const
1313 Cell cell( PreCellularGridSpace::uGetAdd( p, k, x ) );
1314 this->updateCellHelper( cell, k );
1315 ASSERT( uIsValid( cell ) );
1318 //-----------------------------------------------------------------------------
1319 template < DGtal::Dimension dim, typename TInteger>
1321 typename DGtal::KhalimskySpaceND< dim, TInteger>::Cell
1322 DGtal::KhalimskySpaceND< dim, TInteger>::
1323 uGetSub( const Cell & p, DGtal::Dimension k, Integer x ) const
1325 Cell cell( PreCellularGridSpace::uGetSub( p, k, x ) );
1326 this->updateCellHelper( cell, k );
1327 ASSERT( uIsValid( cell ) );
1330 //-----------------------------------------------------------------------------
1331 template < DGtal::Dimension dim, typename TInteger>
1334 DGtal::KhalimskySpaceND< dim, TInteger>::
1335 uDistanceToMax( const Cell & p, DGtal::Dimension k ) const
1337 using KPS = PreCellularGridSpace;
1339 ASSERT( uIsValid(p) );
1340 return ( KPS::uKCoord( myCellUpper, k ) - KPS::uKCoord( p, k ) ) >> 1;
1342 //-----------------------------------------------------------------------------
1343 template < DGtal::Dimension dim, typename TInteger>
1346 DGtal::KhalimskySpaceND< dim, TInteger>::
1347 uDistanceToMin( const Cell & p, DGtal::Dimension k ) const
1349 using KPS = PreCellularGridSpace;
1351 ASSERT( uIsValid(p) );
1352 return ( KPS::uKCoord( p, k ) - KPS::uKCoord( myCellLower, k ) ) >> 1;
1354 //-----------------------------------------------------------------------------
1355 template < DGtal::Dimension dim, typename TInteger>
1357 typename DGtal::KhalimskySpaceND< dim, TInteger>::Cell
1358 DGtal::KhalimskySpaceND< dim, TInteger>::
1359 uTranslation( const Cell & p, const Vector & vec ) const
1361 Cell cell( PreCellularGridSpace::uTranslation( p, vec ) );
1362 this->updateCellHelper( cell );
1363 ASSERT( uIsValid( cell ) );
1366 //-----------------------------------------------------------------------------
1367 template < DGtal::Dimension dim, typename TInteger>
1369 typename DGtal::KhalimskySpaceND< dim, TInteger>::Cell
1370 DGtal::KhalimskySpaceND< dim, TInteger>::
1371 uProjection( const Cell & p, const Cell & bound, DGtal::Dimension k ) const
1373 Cell cell( PreCellularGridSpace::uProjection( p, bound, k ) );
1374 ASSERT( uIsValid( cell ) );
1377 //-----------------------------------------------------------------------------
1378 template < DGtal::Dimension dim, typename TInteger>
1381 DGtal::KhalimskySpaceND< dim, TInteger>::
1382 uProject( Cell & p, const Cell & bound, DGtal::Dimension k ) const
1384 PreCellularGridSpace::uProject( p.myPreCell, bound, k );
1385 ASSERT( uIsValid( p ) );
1387 //-----------------------------------------------------------------------------
1388 template < DGtal::Dimension dim, typename TInteger>
1391 DGtal::KhalimskySpaceND< dim, TInteger>::
1392 uNext( Cell & p, const Cell & lower, const Cell & upper ) const
1394 ASSERT( uIsValid(p) );
1395 ASSERT( uIsValid(lower) );
1396 ASSERT( uIsValid(upper) );
1397 ASSERT( uTopology(p) == uTopology(lower)
1398 && uTopology(p) == uTopology(upper) );
1400 using KPS = PreCellularGridSpace;
1402 DGtal::Dimension k = NumberTraits<Dimension>::ZERO;
1403 if ( KPS::uKCoord( p, k ) == KPS::uKCoord( upper, k ) )
1405 if ( p == upper ) return false;
1406 KPS::uProject( p.myPreCell, lower, k );
1408 for ( k = 1; k < DIM; ++k )
1410 if ( KPS::uKCoord( p, k ) == KPS::uKCoord( upper, k ) )
1411 KPS::uProject( p.myPreCell, lower, k );
1414 KPS::uSetKCoord( p.myPreCell, k, this->returnKCoordHelper( KPS::uKCoord( p, k ) + 2, k ) );
1421 KPS::uSetKCoord( p.myPreCell, k, this->returnKCoordHelper( KPS::uKCoord( p, k ) + 2, k ) );
1425 //-----------------------------------------------------------------------------
1426 ///////////////////////////////////////////////////////////////////////////////
1427 //-----------------------------------------------------------------------------
1428 //-----------------------------------------------------------------------------
1429 template < DGtal::Dimension dim, typename TInteger>
1431 typename DGtal::KhalimskySpaceND< dim, TInteger>::Integer
1432 DGtal::KhalimskySpaceND< dim, TInteger>::
1433 sFirst( const SPreCell & p, DGtal::Dimension k ) const
1437 return myClosure[ k ] == OPEN ?
1438 2 * myLower[ k ] + ( NumberTraits<Integer>::odd( p.coordinates[ k ] ) ? 1 : 2 )
1439 : 2 * myLower[ k ] + ( NumberTraits<Integer>::odd( p.coordinates[ k ] ) ? 1 : 0 );
1441 //-----------------------------------------------------------------------------
1442 template < DGtal::Dimension dim, typename TInteger>
1444 typename DGtal::KhalimskySpaceND< dim, TInteger >::SCell
1445 DGtal::KhalimskySpaceND< dim, TInteger >::
1446 sFirst( const SPreCell & p ) const
1449 for ( Dimension k = 0; k < dimension; ++k )
1450 PreCellularGridSpace::sSetKCoord( cell.mySPreCell, k, sFirst( p, k ) );
1452 PreCellularGridSpace::sSetSign( cell.mySPreCell, PreCellularGridSpace::sSign( p ) );
1456 //-----------------------------------------------------------------------------
1457 template < DGtal::Dimension dim, typename TInteger>
1459 typename DGtal::KhalimskySpaceND< dim, TInteger>::Integer
1460 DGtal::KhalimskySpaceND< dim, TInteger>::
1461 sLast( const SPreCell & p, DGtal::Dimension k ) const
1464 return myClosure[ k ] == CLOSED ?
1465 2 * myUpper[ k ] + ( NumberTraits<Integer>::odd( p.coordinates[ k ] ) ? 1 : 2 )
1466 : 2 * myUpper[ k ] + ( NumberTraits<Integer>::odd( p.coordinates[ k ] ) ? 1 : 0 );
1468 //-----------------------------------------------------------------------------
1469 template < DGtal::Dimension dim, typename TInteger>
1471 typename DGtal::KhalimskySpaceND< dim, TInteger >::SCell
1472 DGtal::KhalimskySpaceND< dim, TInteger >::
1473 sLast( const SPreCell & p ) const
1476 for ( Dimension k = 0; k < dimension; ++k )
1477 PreCellularGridSpace::sSetKCoord( cell.mySPreCell, k, sLast( p, k ) );
1479 PreCellularGridSpace::sSetSign( cell.mySPreCell, PreCellularGridSpace::sSign( p ) );
1483 //-----------------------------------------------------------------------------
1484 template < DGtal::Dimension dim, typename TInteger>
1486 typename DGtal::KhalimskySpaceND< dim, TInteger >::SCell
1487 DGtal::KhalimskySpaceND< dim, TInteger >::
1488 sGetIncr( const SCell & p, DGtal::Dimension k ) const
1490 SCell cell( PreCellularGridSpace::sGetIncr( p, k ) );
1491 this->updateSCellHelper( cell, k );
1492 ASSERT( sIsValid( cell ) );
1495 //-----------------------------------------------------------------------------
1496 template < DGtal::Dimension dim, typename TInteger>
1499 DGtal::KhalimskySpaceND< dim, TInteger >::
1500 sIsMax( const SCell & p, DGtal::Dimension k ) const
1503 ASSERT( sIsInside(p) );
1505 ! this->isDimensionPeriodicHelper( k )
1506 && PreCellularGridSpace::sKCoord( p, k ) >= sLast( p, k );
1508 //-----------------------------------------------------------------------------
1509 template < DGtal::Dimension dim, typename TInteger>
1512 DGtal::KhalimskySpaceND< dim, TInteger>::
1513 sIsInside( const SPreCell & p, DGtal::Dimension k ) const
1515 return cIsInside( p.coordinates, k );
1517 //-----------------------------------------------------------------------------
1518 template < DGtal::Dimension dim, typename TInteger>
1521 DGtal::KhalimskySpaceND< dim, TInteger>::
1522 sIsInside( const SPreCell & p ) const
1524 return cIsInside( p.coordinates );
1526 //-----------------------------------------------------------------------------
1527 template < DGtal::Dimension dim, typename TInteger>
1529 typename DGtal::KhalimskySpaceND< dim, TInteger >::SCell
1530 DGtal::KhalimskySpaceND< dim, TInteger >::
1531 sGetMax( SCell p, DGtal::Dimension k ) const
1533 PreCellularGridSpace::sSetKCoord( p.mySPreCell, k, sLast( p, k ) );
1534 ASSERT( sIsValid( p ) );
1537 //-----------------------------------------------------------------------------
1538 template < DGtal::Dimension dim, typename TInteger>
1540 typename DGtal::KhalimskySpaceND< dim, TInteger >::SCell
1541 DGtal::KhalimskySpaceND< dim, TInteger >::
1542 sGetDecr( const SCell & p, DGtal::Dimension k ) const
1544 SCell cell( PreCellularGridSpace::sGetDecr( p, k ) );
1545 this->updateSCellHelper( cell, k );
1546 ASSERT( sIsValid( cell ) );
1549 //-----------------------------------------------------------------------------
1550 template < DGtal::Dimension dim, typename TInteger>
1553 DGtal::KhalimskySpaceND< dim, TInteger >::
1554 sIsMin( const SCell & p, DGtal::Dimension k ) const
1557 ASSERT( sIsInside(p) );
1559 ! this->isDimensionPeriodicHelper( k )
1560 && PreCellularGridSpace::sKCoord( p, k ) <= sFirst( p, k );
1562 //-----------------------------------------------------------------------------
1563 template < DGtal::Dimension dim, typename TInteger>
1565 typename DGtal::KhalimskySpaceND< dim, TInteger >::SCell
1566 DGtal::KhalimskySpaceND< dim, TInteger >::
1567 sGetMin( SCell p, DGtal::Dimension k ) const
1569 PreCellularGridSpace::sSetKCoord( p.mySPreCell, k, sFirst( p, k ) );
1570 ASSERT( sIsValid( p ) );
1573 //-----------------------------------------------------------------------------
1574 template < DGtal::Dimension dim, typename TInteger>
1576 typename DGtal::KhalimskySpaceND< dim, TInteger >::SCell
1577 DGtal::KhalimskySpaceND< dim, TInteger >::
1578 sGetAdd( const SCell & p, DGtal::Dimension k, Integer x ) const
1580 SCell cell( PreCellularGridSpace::sGetAdd( p, k, x ) );
1581 this->updateSCellHelper( cell, k );
1582 ASSERT( sIsValid( cell ) );
1585 //-----------------------------------------------------------------------------
1586 template < DGtal::Dimension dim, typename TInteger>
1588 typename DGtal::KhalimskySpaceND< dim, TInteger >::SCell
1589 DGtal::KhalimskySpaceND< dim, TInteger >::
1590 sGetSub( const SCell & p, DGtal::Dimension k, Integer x ) const
1592 SCell cell( PreCellularGridSpace::sGetSub( p, k, x ) );
1593 this->updateSCellHelper( cell, k );
1594 ASSERT( sIsValid( cell ) );
1597 //-----------------------------------------------------------------------------
1598 template < DGtal::Dimension dim, typename TInteger>
1601 DGtal::KhalimskySpaceND< dim, TInteger >::
1602 sDistanceToMax( const SCell & p, DGtal::Dimension k ) const
1604 using KPS = PreCellularGridSpace;
1606 ASSERT( sIsValid( p ) );
1607 return ( KPS::uKCoord( myCellUpper, k ) - KPS::sKCoord( p, k ) ) >> 1;
1609 //-----------------------------------------------------------------------------
1610 template < DGtal::Dimension dim, typename TInteger>
1613 DGtal::KhalimskySpaceND< dim, TInteger >::
1614 sDistanceToMin( const SCell & p, DGtal::Dimension k ) const
1616 using KPS = PreCellularGridSpace;
1618 ASSERT( sIsValid( p ) );
1619 return ( KPS::sKCoord( p, k ) - KPS::uKCoord( myCellLower, k ) ) >> 1;
1621 //-----------------------------------------------------------------------------
1622 template < DGtal::Dimension dim, typename TInteger>
1624 typename DGtal::KhalimskySpaceND< dim, TInteger >::SCell
1625 DGtal::KhalimskySpaceND< dim, TInteger >::
1626 sTranslation( const SCell & p, const Vector & vec ) const
1628 SCell cell( PreCellularGridSpace::sTranslation( p, vec ) );
1629 this->updateSCellHelper( cell );
1630 ASSERT( sIsValid( cell ) );
1633 //-----------------------------------------------------------------------------
1634 template < DGtal::Dimension dim, typename TInteger>
1636 typename DGtal::KhalimskySpaceND< dim, TInteger >::SCell
1637 DGtal::KhalimskySpaceND< dim, TInteger >::
1638 sProjection( const SCell & p, const SCell & bound, DGtal::Dimension k ) const
1640 SCell cell( PreCellularGridSpace::sProjection( p, bound, k ) );
1641 ASSERT( sIsValid( cell ) );
1644 //-----------------------------------------------------------------------------
1645 template < DGtal::Dimension dim, typename TInteger>
1648 DGtal::KhalimskySpaceND< dim, TInteger >::
1649 sProject( SCell & p, const SCell & bound, DGtal::Dimension k ) const
1651 PreCellularGridSpace::sProject( p.mySPreCell, bound, k );
1652 ASSERT( sIsValid( p ) );
1654 //-----------------------------------------------------------------------------
1655 template < DGtal::Dimension dim, typename TInteger>
1658 DGtal::KhalimskySpaceND< dim, TInteger >::
1659 sNext( SCell & p, const SCell & lower, const SCell & upper ) const
1661 ASSERT( sIsValid(p) );
1662 ASSERT( sIsValid(lower) );
1663 ASSERT( sIsValid(upper) );
1664 ASSERT( sTopology(p) == sTopology(lower)
1665 && sTopology(p) == sTopology(upper) );
1667 using KPS = PreCellularGridSpace;
1669 DGtal::Dimension k = NumberTraits<Dimension>::ZERO;
1670 if ( KPS::sKCoord( p, k ) == KPS::sKCoord( upper, k ) )
1672 if ( p == upper ) return false;
1673 KPS::sProject( p.mySPreCell, lower, k );
1675 for ( k = 1; k < DIM; ++k )
1677 if ( KPS::sKCoord( p, k ) == KPS::sKCoord( upper, k ) )
1678 KPS::sProject( p.mySPreCell, lower, k );
1681 KPS::sSetKCoord( p.mySPreCell, k, this->returnKCoordHelper( KPS::sKCoord( p, k ) + 2, k ) );
1688 KPS::sSetKCoord( p.mySPreCell, k, this->returnKCoordHelper( KPS::sKCoord( p, k ) + 2, k ) );
1692 //-----------------------------------------------------------------------------
1693 // ----------------------- Neighborhood services --------------------------
1694 //-----------------------------------------------------------------------------
1695 template < DGtal::Dimension dim, typename TInteger>
1697 typename DGtal::KhalimskySpaceND< dim, TInteger >::Cells
1698 DGtal::KhalimskySpaceND< dim, TInteger >::
1699 uNeighborhood( const Cell & c ) const
1701 ASSERT( uIsValid(c) );
1705 for ( DGtal::Dimension k = 0; k < DIM; ++k )
1707 if ( ! uIsMin( c, k ) )
1708 N.push_back( uGetDecr( c, k ) );
1709 if ( ! uIsMax( c, k ) )
1710 N.push_back( uGetIncr( c, k ) );
1714 //-----------------------------------------------------------------------------
1715 template < DGtal::Dimension dim, typename TInteger>
1717 typename DGtal::KhalimskySpaceND< dim, TInteger >::SCells
1718 DGtal::KhalimskySpaceND< dim, TInteger >::
1719 sNeighborhood( const SCell & c ) const
1721 ASSERT( sIsValid(c) );
1725 for ( DGtal::Dimension k = 0; k < DIM; ++k )
1727 if ( ! sIsMin( c, k ) )
1728 N.push_back( sGetDecr( c, k ) );
1729 if ( ! sIsMax( c, k ) )
1730 N.push_back( sGetIncr( c, k ) );
1734 //-----------------------------------------------------------------------------
1735 template < DGtal::Dimension dim, typename TInteger>
1737 typename DGtal::KhalimskySpaceND< dim, TInteger >::Cells
1738 DGtal::KhalimskySpaceND< dim, TInteger >::
1739 uProperNeighborhood( const Cell & c ) const
1741 ASSERT( uIsValid(c) );
1744 for ( DGtal::Dimension k = 0; k < DIM; ++k )
1746 if ( ! uIsMin( c, k ) )
1747 N.push_back( uGetDecr( c, k ) );
1748 if ( ! uIsMax( c, k ) )
1749 N.push_back( uGetIncr( c, k ) );
1753 //-----------------------------------------------------------------------------
1754 template < DGtal::Dimension dim, typename TInteger>
1756 typename DGtal::KhalimskySpaceND< dim, TInteger >::SCells
1757 DGtal::KhalimskySpaceND< dim, TInteger >::
1758 sProperNeighborhood( const SCell & c ) const
1760 ASSERT( sIsValid(c) );
1763 for ( DGtal::Dimension k = 0; k < DIM; ++k )
1765 if ( ! sIsMin( c, k ) )
1766 N.push_back( sGetDecr( c, k ) );
1767 if ( ! sIsMax( c, k ) )
1768 N.push_back( sGetIncr( c, k ) );
1772 //-----------------------------------------------------------------------------
1773 template < DGtal::Dimension dim, typename TInteger>
1775 typename DGtal::KhalimskySpaceND< dim, TInteger >::Cell
1776 DGtal::KhalimskySpaceND< dim, TInteger >::
1777 uAdjacent( const Cell & p, DGtal::Dimension k, bool up ) const
1780 ASSERT( uIsValid(p) );
1781 ASSERT( ( up && !uIsMax(p, k) ) || ( !up && !uIsMin(p, k) ) );
1782 return up ? uGetIncr( p, k ) : uGetDecr( p, k );
1784 //-----------------------------------------------------------------------------
1785 template < DGtal::Dimension dim, typename TInteger>
1787 typename DGtal::KhalimskySpaceND< dim, TInteger >::SCell
1788 DGtal::KhalimskySpaceND< dim, TInteger >::
1789 sAdjacent( const SCell & p, DGtal::Dimension k, bool up ) const
1792 ASSERT( sIsValid(p) );
1793 ASSERT( ( up && !sIsMax(p, k) ) || ( !up && !sIsMin(p, k) ) );
1794 return up ? sGetIncr( p, k ) : sGetDecr( p, k );
1797 // ----------------------- Incidence services --------------------------
1798 //-----------------------------------------------------------------------------
1799 template < DGtal::Dimension dim, typename TInteger>
1801 typename DGtal::KhalimskySpaceND< dim, TInteger >::Cell
1802 DGtal::KhalimskySpaceND< dim, TInteger >::
1803 uIncident( const Cell & c, DGtal::Dimension k, bool up ) const
1806 ASSERT( uIsValid(c) );
1807 ASSERT( this->isDimensionPeriodicHelper( k ) || ( ! up ) || ( uKCoord( c, k ) < uKCoord( myCellUpper, k ) ) );
1808 ASSERT( this->isDimensionPeriodicHelper( k ) || ( up ) || ( uKCoord( myCellLower, k ) < uKCoord( c, k ) ) );
1810 Cell cell( PreCellularGridSpace::uIncident( c, k, up ) );
1811 this->updateCellHelper( cell, k );
1815 //-----------------------------------------------------------------------------
1816 template < DGtal::Dimension dim, typename TInteger>
1818 typename DGtal::KhalimskySpaceND< dim, TInteger >::SCell
1819 DGtal::KhalimskySpaceND< dim, TInteger >::
1820 sIncident( const SCell & c, DGtal::Dimension k, bool up ) const
1823 ASSERT( sIsValid(c) );
1824 ASSERT( this->isDimensionPeriodicHelper( k ) || ( ! up ) || ( sKCoord( c, k ) < uKCoord( myCellUpper, k ) ) );
1825 ASSERT( this->isDimensionPeriodicHelper( k ) || ( up ) || ( uKCoord( myCellLower, k ) < sKCoord( c, k ) ) );
1827 SCell cell( PreCellularGridSpace::sIncident( c, k, up ) );
1828 this->updateSCellHelper( cell, k );
1832 //-----------------------------------------------------------------------------
1833 template < DGtal::Dimension dim, typename TInteger>
1835 typename DGtal::KhalimskySpaceND< dim, TInteger >::Cells
1836 DGtal::KhalimskySpaceND< dim, TInteger >::
1837 uLowerIncident( const Cell & c ) const
1839 ASSERT( uIsValid(c) );
1842 for ( DirIterator q = uDirs( c ); q != 0; ++q )
1844 const DGtal::Dimension k = *q;
1845 if ( this->isDimensionPeriodicHelper( k ) )
1847 N.push_back( uIncident( c, k, false ) );
1848 N.push_back( uIncident( c, k, true ) );
1852 const Integer x = uKCoord( c, k );
1853 if ( PreCellularGridSpace::uKCoord( myCellLower, k ) < x )
1854 N.push_back( uIncident( c, k, false ) );
1855 if ( x < PreCellularGridSpace::uKCoord( myCellUpper, k ) )
1856 N.push_back( uIncident( c, k, true ) );
1861 //-----------------------------------------------------------------------------
1862 template < DGtal::Dimension dim, typename TInteger>
1864 typename DGtal::KhalimskySpaceND< dim, TInteger >::Cells
1865 DGtal::KhalimskySpaceND< dim, TInteger >::
1866 uUpperIncident( const Cell & c ) const
1868 ASSERT( uIsValid(c) );
1871 for ( DirIterator q = uOrthDirs( c ); q != 0; ++q )
1873 const DGtal::Dimension k = *q;
1874 if ( this->isDimensionPeriodicHelper( k ) )
1876 N.push_back( uIncident( c, k, false ) );
1877 N.push_back( uIncident( c, k, true ) );
1881 const Integer x = uKCoord( c, k );
1882 if ( PreCellularGridSpace::uKCoord( myCellLower, k ) < x )
1883 N.push_back( uIncident( c, k, false ) );
1884 if ( x < PreCellularGridSpace::uKCoord( myCellUpper, k ) )
1885 N.push_back( uIncident( c, k, true ) );
1890 //-----------------------------------------------------------------------------
1891 template < DGtal::Dimension dim, typename TInteger>
1893 typename DGtal::KhalimskySpaceND< dim, TInteger >::SCells
1894 DGtal::KhalimskySpaceND< dim, TInteger >::
1895 sLowerIncident( const SCell & c ) const
1897 ASSERT( sIsValid(c) );
1900 for ( DirIterator q = sDirs( c ); q != 0; ++q )
1902 const DGtal::Dimension k = *q;
1903 if ( this->isDimensionPeriodicHelper( k ) )
1905 N.push_back( sIncident( c, k, false ) );
1906 N.push_back( sIncident( c, k, true ) );
1910 const Integer x = sKCoord( c, k );
1911 if ( PreCellularGridSpace::uKCoord( myCellLower, k ) < x )
1912 N.push_back( sIncident( c, k, false ) );
1913 if ( x < PreCellularGridSpace::uKCoord( myCellUpper, k ) )
1914 N.push_back( sIncident( c, k, true ) );
1919 //-----------------------------------------------------------------------------
1920 template < DGtal::Dimension dim, typename TInteger>
1922 typename DGtal::KhalimskySpaceND< dim, TInteger >::SCells
1923 DGtal::KhalimskySpaceND< dim, TInteger >::
1924 sUpperIncident( const SCell & c ) const
1926 ASSERT( sIsValid(c) );
1929 for ( DirIterator q = sOrthDirs( c ); q != 0; ++q )
1931 const DGtal::Dimension k = *q;
1932 if ( this->isDimensionPeriodicHelper( k ) )
1934 N.push_back( sIncident( c, k, false ) );
1935 N.push_back( sIncident( c, k, true ) );
1939 const Integer x = sKCoord( c, k );
1940 if ( PreCellularGridSpace::uKCoord( myCellLower, k ) < x )
1941 N.push_back( sIncident( c, k, false ) );
1942 if ( x < PreCellularGridSpace::uKCoord( myCellUpper, k ) )
1943 N.push_back( sIncident( c, k, true ) );
1948 //-----------------------------------------------------------------------------
1949 template < DGtal::Dimension dim, typename TInteger>
1952 DGtal::KhalimskySpaceND< dim, TInteger >::
1953 uAddFaces( Cells& faces, const Cell& c, Dimension axis ) const
1955 using KPS = PreCellularGridSpace;
1957 const DGtal::Dimension dim_of_c = uDim( c );
1958 if ( axis >= dim_of_c ) return;
1960 DirIterator q = uDirs( c );
1961 for ( Dimension i = 0; i < axis; ++i ) ++q;
1963 // We test incident cells existence within the current Khalimsky space.
1964 const Integer x = KPS::uKCoord( c, *q );
1965 bool has_f1 = this->isDimensionPeriodicHelper( *q ) || KPS::uKCoord( myCellLower, *q ) < x ;
1966 bool has_f2 = this->isDimensionPeriodicHelper( *q ) || x < KPS::uKCoord( myCellUpper, *q ) ;
1969 if ( has_f1 ) f1 = uIncident( c, *q, false );
1970 if ( has_f2 ) f2 = uIncident( c, *q, true );
1972 if ( has_f1 ) faces.push_back( f1 );
1973 if ( has_f2 ) faces.push_back( f2 );
1975 if ( has_f1 ) uAddFaces( faces, f1, axis );
1976 if ( has_f2 ) uAddFaces( faces, f2, axis );
1978 uAddFaces( faces, c, axis+1 );
1980 //-----------------------------------------------------------------------------
1981 template < DGtal::Dimension dim, typename TInteger>
1984 DGtal::KhalimskySpaceND< dim, TInteger >::
1985 uAddCoFaces( Cells& cofaces, const Cell& c, Dimension axis ) const
1987 using KPS = PreCellularGridSpace;
1989 const DGtal::Dimension dim_of_c = uDim( c );
1990 if ( axis >= dimension - dim_of_c ) return;
1992 DirIterator q = uOrthDirs( c );
1993 for ( Dimension i = 0; i < axis; ++i ) ++q;
1995 // We test incident cells existence within the current Khalimsky space.
1996 const Integer x = KPS::uKCoord( c, *q );
1997 bool has_f1 = this->isDimensionPeriodicHelper( *q ) || KPS::uKCoord( myCellLower, *q ) < x ;
1998 bool has_f2 = this->isDimensionPeriodicHelper( *q ) || x < KPS::uKCoord( myCellUpper, *q ) ;
2001 if ( has_f1 ) f1 = uIncident( c, *q, false );
2002 if ( has_f2 ) f2 = uIncident( c, *q, true );
2004 if ( has_f1 ) cofaces.push_back( f1 );
2005 if ( has_f2 ) cofaces.push_back( f2 );
2007 if ( has_f1 ) uAddCoFaces( cofaces, f1, axis );
2008 if ( has_f2 ) uAddCoFaces( cofaces, f2, axis );
2010 uAddCoFaces( cofaces, c, axis+1 );
2012 //-----------------------------------------------------------------------------
2013 template < DGtal::Dimension dim, typename TInteger>
2015 typename DGtal::KhalimskySpaceND< dim, TInteger >::Cells
2016 DGtal::KhalimskySpaceND< dim, TInteger >::
2017 uFaces( const Cell & c ) const
2019 ASSERT( uIsValid(c) );
2022 uAddFaces( N, c, 0 );
2025 //-----------------------------------------------------------------------------
2026 template < DGtal::Dimension dim, typename TInteger>
2028 typename DGtal::KhalimskySpaceND< dim, TInteger >::Cells
2029 DGtal::KhalimskySpaceND< dim, TInteger >::
2030 uCoFaces( const Cell & c ) const
2032 ASSERT( uIsValid(c) );
2035 uAddCoFaces( N, c, 0 );
2038 //-----------------------------------------------------------------------------
2039 template < DGtal::Dimension dim, typename TInteger>
2042 DGtal::KhalimskySpaceND< dim, TInteger >::
2043 sDirect( const SCell & p, DGtal::Dimension k ) const
2045 return PreCellularGridSpace::sDirect( p, k );
2047 //-----------------------------------------------------------------------------
2048 template < DGtal::Dimension dim, typename TInteger>
2050 typename DGtal::KhalimskySpaceND< dim, TInteger >::SCell
2051 DGtal::KhalimskySpaceND< dim, TInteger >::
2052 sDirectIncident( const SCell & p, DGtal::Dimension k ) const
2054 using KPS = PreCellularGridSpace;
2057 ASSERT( sIsValid(p) );
2058 ASSERT( this->isDimensionPeriodicHelper( k ) || ( ! KPS::sDirect( p, k ) ) || ( KPS::sKCoord( p, k ) < KPS::uKCoord( myCellUpper, k ) ) );
2059 ASSERT( this->isDimensionPeriodicHelper( k ) || ( KPS::sDirect( p, k ) ) || ( KPS::uKCoord( myCellLower, k ) < KPS::sKCoord( p, k ) ) );
2061 SCell cell( KPS::sDirectIncident( p, k ) );
2062 this->updateSCellHelper( cell, k );
2066 //-----------------------------------------------------------------------------
2067 template < DGtal::Dimension dim, typename TInteger>
2069 typename DGtal::KhalimskySpaceND< dim, TInteger >::SCell
2070 DGtal::KhalimskySpaceND< dim, TInteger >::
2071 sIndirectIncident( const SCell & p, DGtal::Dimension k ) const
2073 using KPS = PreCellularGridSpace;
2076 ASSERT( sIsValid(p) );
2077 ASSERT( this->isDimensionPeriodicHelper( k ) || ( KPS::sDirect( p, k ) ) || ( KPS::sKCoord( p, k ) < KPS::uKCoord( myCellUpper, k ) ) );
2078 ASSERT( this->isDimensionPeriodicHelper( k ) || ( ! KPS::sDirect( p, k ) ) || ( KPS::uKCoord( myCellLower, k ) < KPS::sKCoord( p, k ) ) );
2080 SCell cell( KPS::sIndirectIncident( p, k ) );
2081 this->updateSCellHelper( cell, k );
2089 //-----------------------------------------------------------------------------
2090 template < DGtal::Dimension dim, typename TInteger>
2093 DGtal::KhalimskySpaceND< dim, TInteger>::
2094 selfDisplay ( std::ostream & out ) const
2096 out << "[KhalimskySpaceND<" << dimension << ">] { ";
2098 for ( Dimension i = 0; i < dimension; ++i )
2099 out << ( myClosure[i] == OPEN ? "OPEN " : ( myClosure[i] == CLOSED ? "CLOSED " : "PERIODIC " ) );
2101 out << "lower = " << myLower << ", ";
2102 out << "upper = " << myUpper;
2106 //-----------------------------------------------------------------------------
2107 template < DGtal::Dimension dim, typename TInteger>
2110 DGtal::KhalimskySpaceND< dim, TInteger>::
2118 ///////////////////////////////////////////////////////////////////////////////
2119 // Implementation of inline functions //
2120 template < DGtal::Dimension dim, typename TInteger>
2123 DGtal::operator<< ( std::ostream & out,
2124 const KhalimskySpaceND< dim, TInteger> & object )
2126 object.selfDisplay( out );
2131 ///////////////////////////////////////////////////////////////////////////////