ITK  6.0.0
Insight Toolkit
itkMultivariateLegendrePolynomial.h
Go to the documentation of this file.
1 /*=========================================================================
2  *
3  * Copyright NumFOCUS
4  *
5  * Licensed under the Apache License, Version 2.0 (the "License");
6  * you may not use this file except in compliance with the License.
7  * You may obtain a copy of the License at
8  *
9  * https://www.apache.org/licenses/LICENSE-2.0.txt
10  *
11  * Unless required by applicable law or agreed to in writing, software
12  * distributed under the License is distributed on an "AS IS" BASIS,
13  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14  * See the License for the specific language governing permissions and
15  * limitations under the License.
16  *
17  *=========================================================================*/
18 #ifndef itkMultivariateLegendrePolynomial_h
19 #define itkMultivariateLegendrePolynomial_h
20 
21 #include "itkIntTypes.h"
22 #include "itkIndent.h"
23 #include <vector>
24 #include "itkArray.h"
25 #include "ITKPolynomialsExport.h"
26 
27 namespace itk
28 {
77 class ITKPolynomials_EXPORT MultivariateLegendrePolynomial
78 {
79 public:
81 
82  using DoubleArrayType = std::vector<double>;
83  using ULongArrayType = std::vector<unsigned long>;
84  using LongArrayType = std::vector<long>;
85 
88 
92 
96 
98  MultivariateLegendrePolynomial(unsigned int dimension, unsigned int degree, const DomainSizeType & domainSize);
99 
102 
104  unsigned int
105  GetDimension() const
106  {
107  return m_Dimension;
108  }
109 
111  unsigned int
112  GetDegree() const
113  {
114  return m_Degree;
115  }
116 
123  unsigned int
125  {
126  return m_NumberOfCoefficients;
127  }
128 
130  const DomainSizeType &
132  {
133  return m_DomainSize;
134  }
135 
142  {
143  public:
144  CoefficientVectorSizeMismatch(const size_t given, const size_t required)
145  : m_Required{ required }
146  , m_Given{ given }
147  {}
148 
149  size_t m_Required;
150  size_t m_Given;
151  };
152 
157  void
158  SetCoefficients(const CoefficientArrayType & coefficients);
159 
160  void
161  SetCoefficients(const ParametersType & coefficients);
162 
164  const CoefficientArrayType &
165  GetCoefficients() const;
166 
169  double
171  {
172  if (m_Dimension == 2)
173  {
174  if (index[1] != m_PrevY)
175  {
176  // normalized y [-1, 1]
177  const double norm_y = m_NormFactor[1] * static_cast<double>(index[1] - 1);
178  this->CalculateXCoef(norm_y, m_CoefficientArray);
179  m_PrevY = index[1];
180  }
183  // normalized x [-1, 1]
184  const double norm_x = m_NormFactor[0] * static_cast<double>(index[0] - 1);
185 
186  return LegendreSum(norm_x, m_Degree, m_CachedXCoef);
187  }
188  else if (m_Dimension == 3)
189  {
190  if (index[2] != m_PrevZ)
191  {
192  // normalized z [-1, 1]
193  const double norm_z = m_NormFactor[2] * static_cast<double>(index[2] - 1);
194  this->CalculateYCoef(norm_z, m_CoefficientArray);
195  m_PrevZ = index[2];
196  }
197 
198  if (index[1] != m_PrevY)
199  {
200  // normalized y [-1, 1]
201  const double norm_y = m_NormFactor[1] * static_cast<double>(index[1] - 1);
202  this->CalculateXCoef(norm_y, m_CachedYCoef);
203  m_PrevY = index[1];
204  }
205 
206  // normalized x [-1, 1]
207  const double norm_x = m_NormFactor[0] * static_cast<double>(index[0] - 1);
208  return this->LegendreSum(norm_x, m_Degree, m_CachedXCoef);
209  }
210  return 0;
211  }
212 
214  unsigned int
215  GetNumberOfCoefficients(unsigned int dimension, unsigned int degree);
216 
225  {
226  public:
228  : m_MultivariateLegendrePolynomial(polynomial)
229  , m_Dimension(m_MultivariateLegendrePolynomial->GetDimension())
230  , m_DomainSize(m_MultivariateLegendrePolynomial->GetDomainSize())
231 
232  {
233  m_Index.resize(m_Dimension);
234  std::fill(m_Index.begin(), m_Index.end(), 0);
235  }
236 
237  void
239  {
240  m_IsAtEnd = false;
241  for (unsigned int dim = 0; dim < m_Dimension; ++dim)
242  {
243  m_Index[dim] = 0;
244  }
245  }
246 
247  bool
248  IsAtEnd() const
249  {
250  return m_IsAtEnd;
251  }
252 
255  {
256  for (unsigned int dim = 0; dim < m_Dimension; ++dim)
257  {
258  if (m_Index[dim] < static_cast<int>(m_DomainSize[dim] - 1))
259  {
260  m_Index[dim] += 1;
261  return *this;
262  }
263  else
264  {
265  if (dim == m_Dimension - 1)
266  {
267  m_IsAtEnd = true;
268  break;
269  }
270  else
271  {
272  m_Index[dim] = 0;
273  }
274  }
275  }
276  return *this;
277  }
278 
279  double
280  Get()
281  {
282  return m_MultivariateLegendrePolynomial->Evaluate(m_Index);
283  }
284 
285  private:
287  unsigned int m_Dimension;
290  bool m_IsAtEnd{ false };
291  }; // end of class Iterator
292 
293  void
294  Print(std::ostream & os) const;
295 
296 protected:
297  void
298  PrintSelf(std::ostream & os, Indent indent) const;
299 
300  double
301  LegendreSum(const double x, int n, const CoefficientArrayType & coef, int offset = 0);
302 
303  void
304  CalculateXCoef(double norm_y, const CoefficientArrayType & coef);
305 
306  void
307  CalculateYCoef(double norm_z, const CoefficientArrayType & coef);
308 
309 private:
310  DomainSizeType m_DomainSize{};
311  unsigned int m_Dimension{};
312  unsigned int m_Degree{};
313  unsigned int m_NumberOfCoefficients{};
314 
315  CoefficientArrayType m_CoefficientArray{};
316  CoefficientArrayType m_CachedXCoef{};
317  CoefficientArrayType m_CachedYCoef{};
318  CoefficientArrayType m_CachedZCoef{};
319 
320  DoubleArrayType m_NormFactor{};
321  IndexValueType m_PrevY{};
322  IndexValueType m_PrevZ{};
323 }; // end of class
324 
325 ITKPolynomials_EXPORT std::ostream &
326  operator<<(std::ostream & os, const MultivariateLegendrePolynomial & poly);
327 } // end of namespace itk
328 #endif
itk::MultivariateLegendrePolynomial::CoefficientArrayType
DoubleArrayType CoefficientArrayType
Definition: itkMultivariateLegendrePolynomial.h:87
itk::MultivariateLegendrePolynomial::CoefficientVectorSizeMismatch::m_Given
vcl_size_t m_Given
Definition: itkMultivariateLegendrePolynomial.h:150
itk::MultivariateLegendrePolynomial::CoefficientVectorSizeMismatch
Exception object.
Definition: itkMultivariateLegendrePolynomial.h:141
itk::MultivariateLegendrePolynomial::GetDegree
unsigned int GetDegree() const
Definition: itkMultivariateLegendrePolynomial.h:112
itk::MultivariateLegendrePolynomial::GetDomainSize
const DomainSizeType & GetDomainSize() const
Definition: itkMultivariateLegendrePolynomial.h:131
itk::MultivariateLegendrePolynomial::SimpleForwardIterator::Get
double Get()
Definition: itkMultivariateLegendrePolynomial.h:280
itk::MultivariateLegendrePolynomial
2D and 3D multivariate Legendre Polynomial
Definition: itkMultivariateLegendrePolynomial.h:77
itk::MultivariateLegendrePolynomial::SimpleForwardIterator::m_Index
IndexType m_Index
Definition: itkMultivariateLegendrePolynomial.h:289
itk::MultivariateLegendrePolynomial::SimpleForwardIterator::operator++
SimpleForwardIterator & operator++()
Definition: itkMultivariateLegendrePolynomial.h:254
itk::operator<<
ITKCommon_EXPORT std::ostream & operator<<(std::ostream &out, typename AnatomicalOrientation::CoordinateEnum value)
itk::Indent
Control indentation during Print() invocation.
Definition: itkIndent.h:49
itk::MultivariateLegendrePolynomial::SimpleForwardIterator::m_MultivariateLegendrePolynomial
MultivariateLegendrePolynomial * m_MultivariateLegendrePolynomial
Definition: itkMultivariateLegendrePolynomial.h:286
itk::MultivariateLegendrePolynomial::SimpleForwardIterator::m_DomainSize
DomainSizeType m_DomainSize
Definition: itkMultivariateLegendrePolynomial.h:288
itk::MultivariateLegendrePolynomial::SimpleForwardIterator::IsAtEnd
bool IsAtEnd() const
Definition: itkMultivariateLegendrePolynomial.h:248
itk::IndexValueType
long IndexValueType
Definition: itkIntTypes.h:93
itk::MultivariateLegendrePolynomial::DoubleArrayType
std::vector< double > DoubleArrayType
Definition: itkMultivariateLegendrePolynomial.h:82
itk::MultivariateLegendrePolynomial::DomainSizeType
ULongArrayType DomainSizeType
Definition: itkMultivariateLegendrePolynomial.h:94
itk::MultivariateLegendrePolynomial::ULongArrayType
std::vector< unsigned long > ULongArrayType
Definition: itkMultivariateLegendrePolynomial.h:83
itk::MultivariateLegendrePolynomial::CoefficientVectorSizeMismatch::m_Required
vcl_size_t m_Required
Definition: itkMultivariateLegendrePolynomial.h:149
itkIndent.h
itk::MultivariateLegendrePolynomial::IndexType
LongArrayType IndexType
Definition: itkMultivariateLegendrePolynomial.h:95
itk::MultivariateLegendrePolynomial::GetNumberOfCoefficients
unsigned int GetNumberOfCoefficients() const
Definition: itkMultivariateLegendrePolynomial.h:124
itk::MultivariateLegendrePolynomial::CoefficientVectorSizeMismatch::CoefficientVectorSizeMismatch
CoefficientVectorSizeMismatch(const vcl_size_t given, const vcl_size_t required)
Definition: itkMultivariateLegendrePolynomial.h:144
itk::MultivariateLegendrePolynomial::SimpleForwardIterator::SimpleForwardIterator
SimpleForwardIterator(MultivariateLegendrePolynomial *polynomial)
Definition: itkMultivariateLegendrePolynomial.h:227
itkIntTypes.h
itk::MultivariateLegendrePolynomial::SimpleForwardIterator::m_Dimension
unsigned int m_Dimension
Definition: itkMultivariateLegendrePolynomial.h:287
itk::MultivariateLegendrePolynomial::SimpleForwardIterator
Iterator which only supports forward iteration and Begin(), IsAtEnd(), and Get() method which work ju...
Definition: itkMultivariateLegendrePolynomial.h:224
itkArray.h
itk::MultivariateLegendrePolynomial::Evaluate
double Evaluate(IndexType &index)
Definition: itkMultivariateLegendrePolynomial.h:170
itk
The "itk" namespace contains all Insight Segmentation and Registration Toolkit (ITK) classes....
Definition: itkAnatomicalOrientation.h:29
itk::Array< double >
itk::MultivariateLegendrePolynomial::LongArrayType
std::vector< long > LongArrayType
Definition: itkMultivariateLegendrePolynomial.h:84
itk::MultivariateLegendrePolynomial::SimpleForwardIterator::Begin
void Begin()
Definition: itkMultivariateLegendrePolynomial.h:238
itk::MultivariateLegendrePolynomial::GetDimension
unsigned int GetDimension() const
Definition: itkMultivariateLegendrePolynomial.h:105