DGtal  1.2.0
BoundedLatticePolytope.h
1 
17 #pragma once
18 
31 #if defined(BoundedLatticePolytope_RECURSES)
32 #error Recursive header files inclusion detected in BoundedLatticePolytope.h
33 #else // defined(BoundedLatticePolytope_RECURSES)
35 #define BoundedLatticePolytope_RECURSES
36 
37 #if !defined BoundedLatticePolytope_h
39 #define BoundedLatticePolytope_h
40 
42 // Inclusions
43 #include <iostream>
44 #include <list>
45 #include <vector>
46 #include <string>
47 #include "DGtal/base/Common.h"
48 #include "DGtal/kernel/CSpace.h"
49 #include "DGtal/kernel/domains/HyperRectDomain.h"
50 #include "DGtal/arithmetic/IntegerComputer.h"
51 #include "DGtal/arithmetic/ClosedIntegerHalfPlane.h"
53 
54 namespace DGtal
55 {
56 
58  // template class BoundedLatticePolytope
73  template < typename TSpace >
75  {
77 
78  public:
80  typedef TSpace Space;
81  typedef typename Space::Integer Integer;
82  typedef typename Space::Point Point;
83  typedef typename Space::Vector Vector;
84  typedef std::vector<Vector> InequalityMatrix;
85  typedef std::vector<Integer> InequalityVector;
88 #ifdef WITH_BIGINTEGER
90 #else
91  typedef DGtal::int64_t BigInteger;
92 #endif
93  static const Dimension dimension = Space::dimension;
94 
99  struct UnitSegment {
101  UnitSegment( Dimension d ) : k( d ) {}
102  };
103 
111  };
112 
120  };
121 
127  struct UnitCell {
128  std::vector<Dimension> dims;
129  UnitCell( std::initializer_list<Dimension> l )
130  : dims( l.begin(), l.end() ) {}
131 
138  friend std::ostream&
139  operator<< ( std::ostream & out,
140  const UnitCell & object )
141  {
142  out << "{";
143  for ( Dimension i = 0; i < object.dims.size(); ++i ) out << object.dims[ i ];
144  out << "}";
145  return out;
146  }
147  };
148 
155  std::vector<Dimension> dims;
156  RightStrictUnitCell( std::initializer_list<Dimension> l )
157  : dims( l.begin(), l.end() ) {}
158 
165  friend std::ostream&
166  operator<< ( std::ostream & out,
167  const RightStrictUnitCell & object )
168  {
169  out << "{";
170  for ( Dimension i = 0; i < object.dims.size(); ++i ) out << object.dims[ i ];
171  out << "}";
172  return out;
173  }
174  };
175 
182  std::vector<Dimension> dims;
183  LeftStrictUnitCell( std::initializer_list<Dimension> l )
184  : dims( l.begin(), l.end() ) {}
185 
192  friend std::ostream&
193  operator<< ( std::ostream & out,
194  const LeftStrictUnitCell & object )
195  {
196  out << "{";
197  for ( Dimension i = 0; i < object.dims.size(); ++i ) out << object.dims[ i ];
198  out << "}";
199  return out;
200  }
201  };
202 
205 
210 
215 
220  BoundedLatticePolytope ( const Self & other ) = default;
221 
222 
229  BoundedLatticePolytope( std::initializer_list<Point> l );
230 
239  template <typename PointIterator>
240  BoundedLatticePolytope( PointIterator itB, PointIterator itE );
241 
261  template <typename HalfSpaceIterator>
263  HalfSpaceIterator itB, HalfSpaceIterator itE,
264  bool valid_edge_constraints = false,
265  bool check_duplicate_constraints = false );
266 
286  template <typename HalfSpaceIterator>
287  void init( const Domain& domain,
288  HalfSpaceIterator itB, HalfSpaceIterator itE,
289  bool valid_edge_constraints = false,
290  bool check_duplicate_constraints = false );
291 
292 
305  template <typename PointIterator>
306  bool init( PointIterator itB, PointIterator itE );
307 
313  Self & operator= ( const Self & other ) = default;
314 
316  void clear();
317 
319 
320  // ----------------------- Accessor services ------------------------------
321  public:
324 
326  const Domain& getDomain() const;
327 
329  unsigned int nbHalfSpaces() const;
330 
336  const Vector& getA( unsigned int i ) const;
337 
343  Integer getB( unsigned int i ) const;
344 
350  bool isLarge( unsigned int i ) const;
351 
353  const InequalityMatrix& getA() const;
354 
356  const InequalityVector& getB() const;
360  const std::vector<bool>& getI() const;
361 
366  bool canBeSummed() const;
367 
369 
370  // ----------------------- Check point services ------------------------------
371  public:
372 
375 
380  bool isInside( const Point& p ) const;
381 
388  bool isDomainPointInside( const Point& p ) const;
389 
394  bool isInterior( const Point& p ) const;
395 
400  bool isBoundary( const Point& p ) const;
401 
403 
404  // ----------------------- Modification services ------------------------------
405  public:
406 
409 
413 
426  unsigned int cut( Dimension k, bool pos, Integer b, bool large = true );
427 
445  unsigned int cut( const Vector& a, Integer b, bool large = true,
446  bool valid_edge_constraint = false );
447 
464  unsigned int cut( const HalfSpace & hs, bool large = true,
465  bool valid_edge_constraint = false );
466 
471  void swap( BoundedLatticePolytope & other );
472 
473 
480 
488 
496 
504 
512 
520 
529 
530  // ----------------------- Enumeration services ------------------------------
531  public:
532 
535 
543  Integer count() const;
544 
556 
568 
579  Integer countWithin( Point low, Point hi ) const;
580 
598 
607  void getPoints( std::vector<Point>& pts ) const;
608 
617  void getInteriorPoints( std::vector<Point>& pts ) const;
618 
627  void getBoundaryPoints( std::vector<Point>& pts ) const;
628 
639  template <typename PointSet>
640  void insertPoints( PointSet& pts_set ) const;
641 
643 
644 
645  // ----------------------- Interface --------------------------------------
646  public:
649 
654  void selfDisplay ( std::ostream & out ) const;
655 
662  bool isValid() const;
663 
667  std::string className() const;
668 
670 
671  // ------------------------- Protected Datas ------------------------------
672  protected:
680  std::vector<bool> I;
683 
684  // ------------------------- Private Datas --------------------------------
685  private:
686 
687 
688  // ------------------------- Internals ------------------------------------
689  private:
697 
704 
711 
712  }; // end of class BoundedLatticePolytope
713 
714  namespace detail {
723  template <DGtal::Dimension N, typename TInteger>
725  typedef TInteger Integer;
727  typedef typename Space::Point Point;
728  typedef typename Space::Vector Vector;
731 
744  static void
745  addEdgeConstraint( Polytope& , unsigned int , unsigned int ,
746  const std::vector<Point>& )
747  {
748  trace.error() << "[BoundedLatticePolytopeHelper::addEdgeConstraint]"
749  << " this method is only implemented in 3D." << std::endl;
750  }
751 
754  static
755  Vector crossProduct( const Vector& , const Vector& )
756  {
757  trace.error() << "[BoundedLatticePolytopeHelper::crossProduct]"
758  << " this method is only implemented in 3D." << std::endl;
759  return Vector::zero;
760  }
761  };
762 
770  template <typename TInteger>
771  struct BoundedLatticePolytopeSpecializer<3, TInteger> {
772  typedef TInteger Integer;
774  typedef typename Space::Point Point;
775  typedef typename Space::Vector Vector;
778 
788  static void
789  addEdgeConstraint( Polytope& P, unsigned int i, unsigned int j,
790  const std::vector<Point>& pts )
791  {
792  Vector ab = pts[ i ] - pts[ j ];
793  for ( int s = 0; s < 2; s++ )
794  for ( Dimension k = 0; k < dimension; ++k )
795  {
796  Vector n = ab.crossProduct( Point::base( k, (s == 0) ? 1 : -1 ) );
797  Integer b = n.dot( pts[ i ] );
798  std::size_t nb_in = 0;
799  for ( auto p : pts ) {
800  Integer v = n.dot( p );
801  if ( v < b ) nb_in++;
802  }
803  if ( nb_in == pts.size() - 2 ) {
804  P.cut( n, b, true, true );
805  }
806  }
807  }
812  static
813  Vector crossProduct( const Vector& v1, const Vector& v2 )
814  {
815  return v1.crossProduct( v2 );
816  }
817  };
818  }
819 
822 
829  template <typename TSpace>
830  std::ostream&
831  operator<< ( std::ostream & out,
832  const BoundedLatticePolytope<TSpace> & object );
833 
834 
840  template <typename TSpace>
843  const BoundedLatticePolytope<TSpace> & P );
844 
845 
853  template <typename TSpace>
857 
865  template <typename TSpace>
869 
877  template <typename TSpace>
881 
889  template <typename TSpace>
893 
901  template <typename TSpace>
905 
913  template <typename TSpace>
917 
919 
920 } // namespace DGtal
921 
922 
924 // Includes inline functions.
925 #include "BoundedLatticePolytope.ih"
926 
927 // //
929 
930 #endif // !defined BoundedLatticePolytope_h
931 
932 #undef BoundedLatticePolytope_RECURSES
933 #endif // else defined(BoundedLatticePolytope_RECURSES)
Aim: Represents an nD lattice polytope, i.e. a convex polyhedron bounded with vertices with integer c...
void init(const Domain &domain, HalfSpaceIterator itB, HalfSpaceIterator itE, bool valid_edge_constraints=false, bool check_duplicate_constraints=false)
Integer countWithin(Point low, Point hi) const
void getInteriorPoints(std::vector< Point > &pts) const
unsigned int nbHalfSpaces() const
BoundedLatticePolytope(PointIterator itB, PointIterator itE)
bool isInside(const Point &p) const
BoundedLatticePolytope(const Domain &domain, HalfSpaceIterator itB, HalfSpaceIterator itE, bool valid_edge_constraints=false, bool check_duplicate_constraints=false)
Integer getB(unsigned int i) const
BoundedLatticePolytope(const Self &other)=default
const std::vector< bool > & getI() const
BOOST_CONCEPT_ASSERT((concepts::CSpace< TSpace >))
void clear()
Clears the polytope.
Self & operator+=(UnitCell c)
unsigned int cut(Dimension k, bool pos, Integer b, bool large=true)
ClosedIntegerHalfPlane< Space > HalfSpace
void swap(BoundedLatticePolytope &other)
std::vector< bool > I
Are inequalities large ?
bool isLarge(unsigned int i) const
unsigned int cut(const Vector &a, Integer b, bool large=true, bool valid_edge_constraint=false)
std::vector< Vector > InequalityMatrix
bool init(PointIterator itB, PointIterator itE)
const Vector & getA(unsigned int i) const
bool internalInitFromSegment2D(Point a, Point b)
BoundedLatticePolytope interiorPolytope() const
unsigned int cut(const HalfSpace &hs, bool large=true, bool valid_edge_constraint=false)
std::vector< Integer > InequalityVector
Self & operator+=(UnitSegment s)
Self & operator+=(RightStrictUnitSegment s)
BoundedLatticePolytope< TSpace > Self
bool internalInitFromTriangle3D(Point a, Point b, Point c)
void getBoundaryPoints(std::vector< Point > &pts) const
InequalityMatrix A
The matrix A in the polytope representation .
bool isBoundary(const Point &p) const
void selfDisplay(std::ostream &out) const
Self & operator+=(RightStrictUnitCell c)
HyperRectDomain< Space > Domain
const InequalityVector & getB() const
Self & operator=(const Self &other)=default
std::string className() const
const Domain & getDomain() const
Self & operator*=(Integer t)
bool internalInitFromSegment3D(Point a, Point b)
Integer countUpTo(Integer max) const
bool isDomainPointInside(const Point &p) const
Self & operator+=(LeftStrictUnitCell c)
BoundedLatticePolytope(std::initializer_list< Point > l)
bool myValidEdgeConstraints
Indicates if Minkowski sums with segments will be valid.
bool isInterior(const Point &p) const
void insertPoints(PointSet &pts_set) const
void getPoints(std::vector< Point > &pts) const
InequalityVector B
The vector B in the polytope representation .
const InequalityMatrix & getA() const
Self & operator+=(LeftStrictUnitSegment s)
static Self base(Dimension k, Component val=1)
auto crossProduct(const PointVector< dim, OtherComponent, OtherStorage > &v) const -> decltype(DGtal::crossProduct(*this, v))
Cross product with a PointVector.
static Self zero
Static const for zero PointVector.
Definition: PointVector.h:1595
TInteger Integer
Arithmetic ring induced by (+,-,*) and Integer numbers.
Definition: SpaceND.h:102
static const Dimension dimension
static constants to store the dimension.
Definition: SpaceND.h:132
std::ostream & error()
DGtal is the top-level namespace which contains all DGtal functions and types.
boost::int64_t int64_t
signed 94-bit integer.
Definition: BasicTypes.h:74
std::ostream & operator<<(std::ostream &out, const ClosedIntegerHalfPlane< TSpace > &object)
DGtal::uint32_t Dimension
Definition: Common.h:137
Trace trace
Definition: Common.h:154
KForm< Calculus, order, duality > operator*(const typename Calculus::Scalar &scalar, const KForm< Calculus, order, duality > &form)
mpz_class BigInteger
Multi-precision integer with GMP implementation.
Definition: BasicTypes.h:79
Circulator< TIterator > operator+(typename IteratorCirculatorTraits< TIterator >::Difference d, Circulator< TIterator > &object)
Definition: Circulator.h:453
friend std::ostream & operator<<(std::ostream &out, const LeftStrictUnitCell &object)
LeftStrictUnitCell(std::initializer_list< Dimension > l)
RightStrictUnitCell(std::initializer_list< Dimension > l)
friend std::ostream & operator<<(std::ostream &out, const RightStrictUnitCell &object)
friend std::ostream & operator<<(std::ostream &out, const UnitCell &object)
UnitCell(std::initializer_list< Dimension > l)
Aim: A half-space specified by a vector N and a constant c. The half-space is the set .
Aim: Defines the concept describing a digital space, ie a cartesian product of integer lines.
Definition: CSpace.h:106
static void addEdgeConstraint(Polytope &P, unsigned int i, unsigned int j, const std::vector< Point > &pts)
static Vector crossProduct(const Vector &v1, const Vector &v2)
Aim: It is just a helper class for BoundedLatticePolytope to add dimension specific static methods.
static Vector crossProduct(const Vector &, const Vector &)
static void addEdgeConstraint(Polytope &, unsigned int, unsigned int, const std::vector< Point > &)
int max(int a, int b)
Domain domain