/*========================================================================= * * Copyright NumFOCUS * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * https://www.apache.org/licenses/LICENSE-2.0.txt * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. * *=========================================================================*/ #ifndef itkShapePriorMAPCostFunction_h #define itkShapePriorMAPCostFunction_h #include "itkShapePriorMAPCostFunctionBase.h" #include "itkGaussianKernelFunction.h" namespace itk { /** \class ShapePriorMAPCostFunction * \brief Represents the maximum aprior (MAP) cost function used * ShapePriorSegmentationLevelSetImageFilter to estimate the shape parameters. * * This class follows the shape and pose parameters estimation developed in [1]. * Note that this class returns the negative log of the MAP function. * Using the negative function make this cost function compatible * with generic optimizers which seeks the minimum of a cost function. * * This class has two template parameters, the feature image type representing the * edge potential map and the pixel type used to * represent the output level set in the ShapePriorSegmentationLevelSetImageFilter. * * \sa ShapePriorSegmentationLevelSetImageFilter * * \par REFERENCES * \par * [1] Leventon, M.E. et al. "Statistical Shape Influence in Geodesic Active Contours", CVPR 2000. * * * \ingroup Numerics Optimizers * \ingroup ITKLevelSets */ template class ITK_TEMPLATE_EXPORT ShapePriorMAPCostFunction : public ShapePriorMAPCostFunctionBase { public: ITK_DISALLOW_COPY_AND_MOVE(ShapePriorMAPCostFunction); /** Standard class type aliases. */ using Self = ShapePriorMAPCostFunction; using Superclass = ShapePriorMAPCostFunctionBase; using Pointer = SmartPointer; using ConstPointer = SmartPointer; /** Method for creation through the object factory. */ itkNewMacro(Self); /** \see LightObject::GetNameOfClass() */ itkOverrideGetNameOfClassMacro(ShapePriorMAPCostFunction); /** ParametersType type alias. * It defines a position in the optimization search space. */ using typename Superclass::ParametersType; /** Type of the feature image representing the edge potential map. */ using typename Superclass::FeatureImageType; using typename Superclass::FeatureImagePointer; /** Type of the return measure value. */ using typename Superclass::MeasureType; /** Dimension constant. */ static constexpr unsigned int ImageDimension = TFeatureImage::ImageDimension; /** Type of pixel used to represent the level set. */ using typename Superclass::PixelType; /** Type of node used to represent the active region around the zero set. */ using typename Superclass::NodeType; /** Type of container used to store the level set nodes. */ using typename Superclass::NodeContainerType; /** Type of the shape signed distance function. */ using typename Superclass::ShapeFunctionType; /** Type of the array for storing shape parameter mean and standard deviation. * FIXME: should be templated. */ using ArrayType = Array; /** Set/Get the array of shape parameters mean. */ itkSetMacro(ShapeParameterMeans, ArrayType); itkGetConstMacro(ShapeParameterMeans, ArrayType); /** Set/Get the array of shape parameters standard deviation. */ itkSetMacro(ShapeParameterStandardDeviations, ArrayType); itkGetConstMacro(ShapeParameterStandardDeviations, ArrayType); /** Set/Get the weights for each term. Default is a vector of all ones. * The weights are applied to terms in the following order: * LogInsideTerm, LogGradientTerm, LogShapePriorTerm and * LogPosePriorTerm. */ using WeightsType = FixedArray; itkSetMacro(Weights, WeightsType); itkGetConstReferenceMacro(Weights, WeightsType); /** Compute the inside term component of the MAP cost function. * In particular, the method sums the number of pixels inside * the current contour (defined by nodes of the active region * that are less than zero) which are outside the shape * specified by the input parameters. */ MeasureType ComputeLogInsideTerm(const ParametersType & parameters) const override; /** Compute the gradient term component of the MAP cost function. * In particular, this method assume that ( 1 - FeatureImage ) approximates * a Gaussian (zero mean, unit variance) along the normal of the evolving contour. * The gradient term is then given by a Laplacian of the goodness of fit of * the Gaussian. */ MeasureType ComputeLogGradientTerm(const ParametersType & parameters) const override; /** Compute the shape prior component of the MAP cost function. * In particular, the method assumes that the shape parameters comes from * independent Gaussian distributions defined by the ShapeParameterMeans * and ShapeParameterVariances array. */ MeasureType ComputeLogShapePriorTerm(const ParametersType & parameters) const override; /** Compute the pose prior component of the MAP cost function. * In particular, this method assumes that the pose parameters are * uniformly distributed and returns a constant of zero. */ MeasureType ComputeLogPosePriorTerm(const ParametersType & parameters) const override; /** Initialize the cost function by making sure that all the components * are present. */ void Initialize() override; protected: ShapePriorMAPCostFunction(); ~ShapePriorMAPCostFunction() override = default; void PrintSelf(std::ostream & os, Indent indent) const override; private: ArrayType m_ShapeParameterMeans{}; ArrayType m_ShapeParameterStandardDeviations{}; WeightsType m_Weights{}; typename GaussianKernelFunction::Pointer m_GaussianFunction{}; }; } // end namespace itk #ifndef ITK_MANUAL_INSTANTIATION # include "itkShapePriorMAPCostFunction.hxx" #endif #endif