% ============================================================================= % The CGAL Reference Manual % Chapter: Geometric Optimisation % Class : CGAL::Width_3 % ----------------------------------------------------------------------------- % file : doc_tex/basic/Optimisation/Optimisation_ref/Width_3.tex % author: Thomas Herrmann, Sven Schönherr % ----------------------------------------------------------------------------- % $CGAL_Chapter: Geometric Optimisation $ % $CGAL_Package: Width_3 $ % $Id$ % $Date$ % ============================================================================= \begin{ccRefClass}{Width_3} \ccIndexSubitem [t]{width}{of 3D point set} \ccIndexSubitem [t]{point set}{3D width of} \ccIndexSubitemSeeAlso[t]{polyhedron}{width of 3D point set} \ccIndexSubitem [t]{optimal distances}{width of 3D point set} \ccSaveThreeColumns % ----------------------------------------------------------------------------- \ccDefinition Given a set of points $\mathcal{S}=\left\{p_1,\ldots , p_n\right\}$ in $\R^3$. The width of $\mathcal{S}$, denoted as $\mathcal{W(S)}$, is defined as the minimum distance between two parallel planes of support of $\mathit{conv(\mathcal{S})}$; where $\mathit{conv(\mathcal{S})}$ denotes the convex hull of $\mathcal{S}$. The width in direction $\mathbf{d}$, denoted as $\mathcal{W}_d\mathcal{(S)}$, is the distance between two parallel planes of support of $\mathit{conv(\mathcal{S})}$, which are orthogonal to $\mathbf{d}$. Subject to the applications of the width algorithm, several objects might be interesting: \begin{enumerate} \item The two parallel planes of support such that the distance between them is as small as possible. These planes are called width-planes in further considerations. \item The width $\mathcal{W(S)}$, i.e., the distance between the width-planes. \item The direction $\mathbf{d}_{opt}$ such that $\mathcal{W(S)}=\mathcal{W}_{d_{opt}}\mathcal{(S)}$ \end{enumerate} \emph{Note:} There might be several optimal build directions. Hence neither the width-planes nor the direction $\mathbf{d}_{opt}$ are unique -- only the width is. \ccInclude{CGAL/Width_3.h} % ----------------------------------------------------------------------------- \ccHeading{Requirements} \ccIndexRequirements The template parameter \ccc{Traits} is a model for \ccc{WidthTraits_3}. We provide the model \ccc{Width_default_traits_3} based on a three-dimensional \cgal~kernel. % ----------------------------------------------------------------------------- \ccTypes \ccIndexClassTypes % All the requirements in this section were redundant with the % description of WidthTraits_3. Removed. L.K. % % According to the two different possiblities to create the width (by an % iterator-range or by a polyhedron), there are slightly different % requirements to the types. Note: If the width of a polyhedron is computed, % then there is no need for a traits class for the convex hull algorithm. For % any additional requirement to the types and functions of the traits class, % especially according to the polyhedron and its structure, see concept % \ccc{WidthTraits_3}. A default traits class \ccc{Width_default_traits_3} % is provided. For the requirements of the convex hull traits class the % reader is referred to the reference page for the concept ConvexHullTraits\_3. % % \paragraph{Creation with Iterator-Range}\hfill\newline \ccSetThreeColumns{typedef typename Traits::ChullTraits}{CHullTraits;}{} \ccThreeToTwo \ccGlueBegin \ccNestedType{Traits}{traits class.} \ccTypedef{typedef typename Traits::Point_3 Point_3;}{point type.} \ccTypedef{typedef typename Traits::Plane_3 Plane_3;}{plane type.} \ccTypedef{typedef typename Traits::Vector_3 Vector_3;}{vector type.} \ccTypedef{typedef typename Traits::RT RT;}{algebraic ring type.} \ccTypedef{typedef typename Traits::ChullTraits ChullTraits;}{traits class for the 3D convex hull algorithm.} \ccGlueEnd % \paragraph{Creation with a Polyhedron}\hfill\newline % \ccSetThreeColumns{typedef Traits::Polyhedron}{Polyhedron;}{} % \ccNestedType{Traits}{typedef to \ccc{Traits}.} % \ccNestedType{Point_3}{typedef to \ccc{Traits::Point_3}. It is assumed that \ccc{InputPolyhedron::Point_3} equals \ccc{Traits::Point_3}.} % \ccNestedType{Plane_3}{typedef to \ccc{Traits::Plane_3}. It is assumed that \ccc{Polyhedron::Plane_3} equals \ccc{Traits::Plane_3}.} % \ccNestedType{Vector_3}{typedef to \ccc{Traits::Vector_3}. It is assumed that \ccc{Plane_3::Normal} equals \ccc{Traits::Vector_3}.} % \ccNestedType{RT}{typedef to \ccc{Traits::RT}. It is assumed that the underlying number type of \ccc{Point_3, Plane_3} and \ccc{Vector_3} is \ccc{RT}.} % \ccGlueEnd % ----------------------------------------------------------------------------- \ccCreation \ccIndexClassCreation \ccCreationVariable{width} \ccSetThreeColumns{Vector_3}{get_build_direction ( );}{} \ccThreeToTwo % Again, redundant. The constructors say it also. Removed. L.K. % A \ccClassTemplateName\ object can be created from an arbitrary point set % $\mathcal{S}$ or from a polyhedron $\mathcal{P}$. In the latter case the % given polyhedron is assumed to be convex. \ccConstructor{ template < class InputIterator > Width_3( InputIterator first, InputIterator beyond);}{ creates a variable \ccVar\ initialized to the width of $\mathcal{S}$ -- with $\mathcal{S}$ being the set of points in the range [\ccc{first},\ccc{beyond}). \ccCommentHeading{Requirement} The value type of \ccc{InputIterator} is \ccc{Point_3}.} \ccConstructor{ template < class Polyhedron > Width_3( Polyhedron& P);}{creates a variable \ccVar\ initialized to the width of the polyhedron $P$. Note that the vertex point coordinates are altered! \ccPrecond $P$ is a convex polyhedron. \ccCommentHeading{Requirement} \ccc{Polyhedron} is a \ccc{CGAL::Polyhedron_3} with facets supporting plane equations where \ccc{Polyhedron::Point_3} $\equiv$ \ccc{Point_3} and \ccc{Polyhedron::Plane_3} $\equiv$ \ccc{Plane_3}.} % ----------------------------------------------------------------------------- \ccAccessFunctions \begin{ccIndexMemberFunctions} \ccIndexMemberFunctionGroup{access} \ccMemberFunction{ void get_squared_width ( RT& width_num, RT& width_denom );}{ returns the squared width. For the reason of exact computation not the width itself is stored, but the \emph{squared} width as a fraction: The numerator in \ccc{width_num} and the denominator in \ccc{width_denom}. The width of the point set $\mathcal{S}$ is $\sqrt{\frac{\ccc{width\_num}}{\ccc{width\_denom}}}$.} \ccMemberFunction{ void get_width_planes ( Plane_3& e1, Plane_3& e2 );}{ The planes \ccc{e1} and \ccc{e2} are the two parallel supporting planes, which distance is minimal (among all such planes).} \ccMemberFunction{ void get_width_coefficients ( RT& A,RT& B,RT& C, RT& D, RT& K );}{The returned coefficients \ccc{A,B,C,D,K} have the property that width-plane \ccc{e1} is given by the equation $Ax+By+Cz+D=0$ and width-plane \ccc{e2} by $Ax+By+Cz+K=0$.} \ccMemberFunction{ Vector_3 get_build_direction ( );}{ returns a direction $\mathbf{d}_{opt}$ such that the width-planes \ccc{e1} and \ccc{e2} are perpendicular to $\mathbf{d}_{opt}$. The width of the point set is minimal in this direction.} % naming convention: variable names are lowercase, so no AllDir. L.K. \ccMemberFunction{ void get_all_build_directions ( std::vector& dir );}{ All the build directions are stored in the vector \ccc{dir}. It might happen that a certain body has several different build directions, but it is also possible to have only one build direction.} \ccMemberFunction{ int get_number_of_optimal_solutions( );}{ returns the number of optimal solutions, i.e., the number of optimal build directions.} \end{ccIndexMemberFunctions} % ----------------------------------------------------------------------------- \ccSeeAlso \ccRefIdfierPage{CGAL::Width_default_traits_3}\\[1ex] \ccRefConceptPage{WidthTraits_3} % ----------------------------------------------------------------------------- \ccImplementation \ccIndexImplementation Since the width of the point set $\mathcal{S}$ and the width of the convex hull of $\mathcal{S}$ ($\mathit{conv(\mathcal{S})}$) is the same, the algorithm uses the 3D convex hull algorithm \cgal\ provides. The width-algorithm is not incremental and therefore inserting and erasing points cause not an `automatic' update of the width. Instead you have to run the width-algorithm again even if the point set is extended by only one new point. \begin{ccAdvanced} \paragraph{Large Numbers.} Because there is no need for dividing values during the algorithm, the numbers can get really huge (all the computations are made using a lot of multiplications). Therefore it is strongly recommended to use a number type that can handle numbers of arbitrary length (e.g., \ccc{leda_integer} in combination with the homogeneous representation of the points). But these large numbers have a disadvantage: Operations on them are slower as greater the number gets. Therefore it is possible to shorten the numbers by using the compiler flag \textsc{-Dsimplify}. For using this option it is required that the underlying number type provides the `modulo' operation. \paragraph{Information Output during the Computations.} If during the algorithm the program should output some information (e.g., during the debugging phase) you can turn on the output information by giving the compiler flag \textsc{debug}. In the file \texttt{width\_assertions.h} you can turn on/off the output of some functions and additional informations by changing the defined values from 0 (no output) to 1 (output available). But then it is required that the $<\!<$-operator has to been overloaded for \ccc{Point_3}, \ccc{Plane_3}, \ccc{Vector_3} and \ccc{RT}. \end{ccAdvanced} % ----------------------------------------------------------------------------- \ccExample \ccIndexSubitem[C]{Width_3}{example} \ccIncludeExampleCode{Width_3/test_width_simplex.cpp} % ----------------------------------------------------------------------------- \ccRestoreThreeColumns \end{ccRefClass} % ===== EOF ===================================================================