Files
tenmon/3rdparty/include/pcl/LinearFit.h
T
2022-04-12 08:17:18 +02:00

252 lines
8.8 KiB
C++

// ____ ______ __
// / __ \ / ____// /
// / /_/ // / / /
// / ____// /___ / /___ PixInsight Class Library
// /_/ \____//_____/ PCL 2.4.23
// ----------------------------------------------------------------------------
// pcl/LinearFit.h - Released 2022-03-12T18:59:29Z
// ----------------------------------------------------------------------------
// This file is part of the PixInsight Class Library (PCL).
// PCL is a multiplatform C++ framework for development of PixInsight modules.
//
// Copyright (c) 2003-2022 Pleiades Astrophoto S.L. All Rights Reserved.
//
// Redistribution and use in both source and binary forms, with or without
// modification, is permitted provided that the following conditions are met:
//
// 1. All redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
//
// 2. All redistributions in binary form must reproduce the above copyright
// notice, this list of conditions and the following disclaimer in the
// documentation and/or other materials provided with the distribution.
//
// 3. Neither the names "PixInsight" and "Pleiades Astrophoto", nor the names
// of their contributors, may be used to endorse or promote products derived
// from this software without specific prior written permission. For written
// permission, please contact info@pixinsight.com.
//
// 4. All products derived from this software, in any form whatsoever, must
// reproduce the following acknowledgment in the end-user documentation
// and/or other materials provided with the product:
//
// "This product is based on software from the PixInsight project, developed
// by Pleiades Astrophoto and its contributors (https://pixinsight.com/)."
//
// Alternatively, if that is where third-party acknowledgments normally
// appear, this acknowledgment must be reproduced in the product itself.
//
// THIS SOFTWARE IS PROVIDED BY PLEIADES ASTROPHOTO AND ITS CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
// TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
// PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL PLEIADES ASTROPHOTO OR ITS
// CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
// EXEMPLARY OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, BUSINESS
// INTERRUPTION; PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; AND LOSS OF USE,
// DATA OR PROFITS) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
// CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
// ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
// POSSIBILITY OF SUCH DAMAGE.
// ----------------------------------------------------------------------------
#ifndef __PCL_LinearFit_h
#define __PCL_LinearFit_h
/// \file pcl/LinearFit.h
#include <pcl/Defs.h>
#include <pcl/Exception.h>
#include <pcl/Math.h>
namespace pcl
{
// ----------------------------------------------------------------------------
class PCL_CLASS StatusMonitor;
/*!
* \class LinearFit
* \brief Robust straight line fitting by minimization of mean absolute
* deviation
*
* Given a set of N data points {xi,yi} for i = {0,...,N-1}, %LinearFit finds
* the parameters a,b of the linear function:
*
* <pre>y = L(x) := a + b*x</pre>
*
* that minimizes mean absolute deviation for all the data points. The \e a
* parameter of L() is the ordinate of its intersection with the Y axis. The
* \e b parameter is the slope of the fitted straight line.
*/
class PCL_CLASS LinearFit
{
public:
/*!
* The \e a parameter of the fitted straight line:
*
* <pre>y = a + b*x</pre>
*
* is the ordinate of its intersection with the Y axis. It represents a
* constant additive pedestal present in the whole dataset.
*/
double a = 0;
/*!
* The \e b parameter is the slope of the fitted straight line:
*
* <pre>y = a + b*x</pre>
*
* If the fitted line passes through two points {x1,y1} and {x2,y2}, then
* its slope is equal to (y2 - y1)/(x2 - x1).
*/
double b = 0;
/*!
* Mean absolute deviation of the linear fit. This is the mean absolute
* deviation computed for all data points with respect to the fitted
* straight line function.
*/
double adev = 0;
/*!
* Returns true iff the fitted straight line model is valid. The model
* function is valid if the slope parameter is finite, i.e., if the fitted
* line is not vertical.
*/
bool IsValid() const
{
return IsFinite( b );
}
/*!
* Evaluates the fitted line function for the specified abscissa \a x.
*/
double operator ()( double x ) const
{
return a + b*x;
}
/*!
* Constructs a default %LinearFit object. The resulting object corresponds
* to a horizontal line crossing at the origin, i.e. the X axis.
*/
LinearFit() = default;
/*!
* Copy constructor.
*/
LinearFit( const LinearFit& ) = default;
/*!
* Constructs a %LinearFit object representing the straight line that passes
* through two points {x1,y1} and {x2,y2}.
*
* \warning Do not specify a vertical line, that is, make sure that
* x1 != x2 w.r.t. the machine epsilon, or this constructor will perform a
* division by zero.
*/
template <typename T>
LinearFit( T x1, T y1, T x2, T y2 )
{
b = double( y2 - y1 )/double( x2 - x1 );
a = (y2 - b*x2 + y1 - b*x1)/2;
adev = 0;
}
/*!
* Constructs a %LinearFit object to fit a straight line for the specified
* set of data points.
*
* \param x %Array of abscissae values.
*
* \param y %Array of ordinate values.
*
* \param n Number of data points. Must be >= 2.
*
* \param status If nonzero, pointer to a StatusMonitor object that will be
* updated during the fitting process. The linear fit process
* is \e unbounded, i.e., the total number of monitoring
* steps cannot be known in advance. The default value is
* zero (no monitoring).
*
* When n >= 3, this constructor fits the straight line that minimizes mean
* absolute deviation for all the source data points. When n == 2, this
* function finds the straight line that passes through the two data points.
* When n < 2, this constructor throws an Error exception.
*/
template <typename T>
LinearFit( const T* x, const T* y, size_type n, StatusMonitor* status = nullptr )
{
if ( n < 2 )
throw Error( "LinearFit::LinearFit(): Less than two data points specified." );
if ( n == 2 )
{
b = double( y[1] - y[0] )/double( x[1] - x[0] );
a = (y[1] - b*x[1] + y[0] - b*x[0])/2;
adev = 0;
}
else
Fit( a, b, adev, x, y, n, status );
}
/*!
* Constructs a %LinearFit object to fit a straight line for the specified
* data containers.
*
* \param x %Container of abscissae values.
*
* \param y %Container of ordinate values.
*
* \param status If nonzero, pointer to a StatusMonitor object that will be
* updated during the fitting process. The linear fit process
* is \e unbounded, i.e., the total number of monitoring
* steps cannot be known in advance. The default value is
* zero (no monitoring).
*
* The number \a n of data points is the minimum container length, i.e.:
*
* <pre>n = Min( x.Length(), y.Length() )</pre>
*
* When n >= 3, this constructor fits the straight line that minimizes mean
* absolute deviation for all the source data points. When n == 2, this
* function finds the straight line that passes through the two data points.
* When n < 2, this constructor throws an Error exception.
*/
template <class C>
LinearFit( const C& x, const C& y, StatusMonitor* status = nullptr )
{
size_type n = Min( x.Length(), y.Length() );
if ( n < 2 )
throw Error( "LinearFit::LinearFit(): Less than two data points specified." );
if ( n == 2 )
{
b = double( y[1] - y[0] )/double( x[1] - x[0] );
a = (y[1] - b*x[1] + y[0] - b*x[0])/2;
adev = 0;
}
else
Fit( a, b, adev, x.Begin(), y.Begin(), n, status );
}
private:
static void Fit( double& a, double& b, double& adev,
const float* fx, const float* fy, size_type n, StatusMonitor* status );
static void Fit( double& a, double& b, double& adev,
const double* fx, const double* fy, size_type n, StatusMonitor* status );
};
// ----------------------------------------------------------------------------
} // pcl
#endif // __LinearFit_h
// ----------------------------------------------------------------------------
// EOF pcl/LinearFit.h - Released 2022-03-12T18:59:29Z