Commit 09db6e4e authored by Roman Tolchenov's avatar Roman Tolchenov
Browse files

Added support for automatic background estimation to the Mantidplot fitting...

Added support for automatic background estimation to the Mantidplot fitting tool. The tool was modified to improve its manageability. Now the functions are accessed not directly by via handlers which help the bookkeeping. re #1184
parent 5ff65260
......@@ -57,7 +57,7 @@ public:
std::string asString()const;
/// Function you want to fit to.
void function(double* out, const double* xValues, const int& nData);
void function(double* out, const double* xValues, const int& nData)const;
/// Derivatives of function with respect to active parameters
void functionDeriv(Jacobian* out, const double* xValues, const int& nData);
/// Derivatives to be used in covariance matrix calculation.
......@@ -142,6 +142,8 @@ public:
void removeFunction(int i, bool del=true);
/// Replace a function
void replaceFunction(int i,IFunction* f);
/// Replace a function
void replaceFunction(const IFunction* f_old,IFunction* f_new);
/// Get the function index
int functionIndex(int i)const;
/// Get the function index
......
......@@ -4,7 +4,7 @@
//----------------------------------------------------------------------
// Includes
//----------------------------------------------------------------------
#include "MantidAPI/IBackgroundFunction.h"
#include "MantidAPI/IFunctionWithLocation.h"
namespace Mantid
{
......@@ -39,7 +39,7 @@ namespace API
class DLLExport IBackgroundFunction : public IFunctionWithLocation
{
public:
virtual void fit(const std::vector<double>& X,const std::vector<double>& Y) = 0;
};
} // namespace API
......
......@@ -26,6 +26,7 @@ class Jacobian;
class ParameterTie;
class IConstraint;
class ParameterReference;
class FunctionHandler;
/** This is an interface to a fitting function - a semi-abstarct class.
Functions derived from IFunction can be used with the Fit algorithm.
IFunction defines the structure of a fitting funtion.
......@@ -100,8 +101,10 @@ class ParameterReference;
class DLLExport IFunction
{
public:
/// Constructor
IFunction():m_handler(NULL){}
/// Virtual destructor
virtual ~IFunction(){}
virtual ~IFunction();
/// Returns the function's name
virtual std::string name()const = 0;
......@@ -111,11 +114,15 @@ public:
virtual operator std::string()const{return asString();}
/// Set the workspace
virtual void setWorkspace(boost::shared_ptr<const API::MatrixWorkspace> workspace,int wi,int xMin,int xMax);
/// Get the workspace
virtual boost::shared_ptr<const API::MatrixWorkspace> getWorkspace()const{return m_workspace;}
/// Get workspace index
virtual int getWorkspaceIndex()const{return m_workspaceIndex;}
/// Iinialize the function
virtual void initialize(){this->init();}
/// Function you want to fit to.
virtual void function(double* out, const double* xValues, const int& nData) = 0;
virtual void function(double* out, const double* xValues, const int& nData)const = 0;
/// Derivatives of function with respect to active parameters
virtual void functionDeriv(Jacobian* out, const double* xValues, const int& nData);
/// Derivatives to be used in covariance matrix calculation. Override this method some of the fitted parameters
......@@ -134,8 +141,6 @@ public:
virtual int nParams()const = 0;
/// Returns the index of parameter name
virtual int parameterIndex(const std::string& name)const = 0;
/// Returns the index of a parameter
//virtual int parameterIndex(const double* p)const = 0;
/// Returns the name of parameter i
virtual std::string parameterName(int i)const = 0;
/// Checks if a parameter has been set explicitly
......@@ -184,7 +189,6 @@ public:
virtual bool removeTie(int i) = 0;
/// Get the tie of i-th parameter
virtual ParameterTie* getTie(int i)const = 0;
/// Get
/// Add a constraint to function
virtual void addConstraint(IConstraint* ic) = 0;
......@@ -214,6 +218,11 @@ public:
/// Check if attribute attName exists
virtual bool hasAttribute(const std::string& IGNORE_IFUNCTION_ARGUMENT(attName))const{return false;}
/// Set a function handler
void setHandler(FunctionHandler* handler);
/// Return the handler
FunctionHandler* getHandler()const{return m_handler;}
protected:
/// Function initialization. Declare function parameters in this method.
......@@ -238,6 +247,9 @@ protected:
/// Upper bin index
int m_xMaxIndex;
/// Pointer to a function handler
FunctionHandler* m_handler;
/// Static reference to the logger class
static Kernel::Logger& g_log;
};
......@@ -272,6 +284,28 @@ protected:
/// Overload operator <<
DLLExport std::ostream& operator<<(std::ostream& ostr,const IFunction& f);
/**
* Classes inherited from FunctionHandler will handle the function.
* The intended purpose is to help with displaying nested composite
* functions in a tree view. This way a display handler shows only
* single function and there is no need to duplicate the function tree
* structure.
*/
class FunctionHandler
{
public:
/// Constructor
FunctionHandler(IFunction* fun):m_fun(fun){}
/// Virtual destructor
virtual ~FunctionHandler(){}
/// abstract init method. It is called after setting handler to the function
virtual void init() = 0;
/// Return the handled function
const IFunction* function()const{return m_fun;}
protected:
IFunction* m_fun;///< pointer to the handled function
};
} // namespace API
} // namespace Mantid
......
......@@ -10,6 +10,7 @@
#include <boost/shared_array.hpp>
#include <sstream>
#include <iostream>
#include <algorithm>
namespace Mantid
{
......@@ -109,7 +110,7 @@ std::string CompositeFunction::asString()const
}
/// Function you want to fit to.
void CompositeFunction::function(double* out, const double* xValues, const int& nData)
void CompositeFunction::function(double* out, const double* xValues, const int& nData)const
{
if (nData <= 0) return;
boost::shared_array<double> tmpOut(new double[nData]);
......@@ -530,6 +531,20 @@ void CompositeFunction::removeFunction(int i, bool del)
}
}
/** Replace a function with a new one. The old function is deleted.
* @param f_old The pointer to the function to replace. If it's not
* a member of this composite function nothing happens
* @param f_new A pointer to the new function
*/
void CompositeFunction::replaceFunction(const IFunction* f_old,IFunction* f_new)
{
std::vector<IFunction*>::const_iterator it =
std::find(m_functions.begin(),m_functions.end(),f_old);
if (it == m_functions.end()) return;
int iFun = it - m_functions.begin();
replaceFunction(iFun,f_new);
}
/** Replace a function with a new one. The old function is deleted.
* @param i The index of the function to replace
* @param f A pointer to the new function
......
......@@ -25,6 +25,17 @@ namespace API
{
Kernel::Logger& IFunction::g_log = Kernel::Logger::get("IFunction");
/**
* Destructor
*/
IFunction::~IFunction()
{
if (m_handler)
{
delete m_handler;
}
}
/** Base class implementation of derivative IFunction throws error. This is to check if such a function is provided
by derivative class. In the derived classes this method must return the derivatives of the resuduals function
(defined in void Fit1D::function(const double*, double*, const double*, const double*, const double*, const int&))
......@@ -325,6 +336,19 @@ std::string IFunction::asString()const
return ostr.str();
}
/** Set a function handler
* @param handler A new handler
*/
void IFunction::setHandler(FunctionHandler* handler)
{
m_handler = handler;
if (handler && handler->function() != this)
{
throw std::runtime_error("Function handler points to a different function");
}
m_handler->init();
}
/**
* Operator <<
* @param ostr The output stream
......@@ -336,5 +360,6 @@ std::ostream& operator<<(std::ostream& ostr,const IFunction& f)
return ostr;
}
} // namespace API
} // namespace Mantid
......@@ -35,7 +35,7 @@ public:
std::string name()const{return "Gauss";}
void function(double* out, const double* xValues, const int& nData)
void function(double* out, const double* xValues, const int& nData)const
{
double c = getParameter("c");
double h = getParameter("h");
......@@ -105,7 +105,7 @@ public:
std::string name()const{return "Linear";}
void function(double* out, const double* xValues, const int& nData)
void function(double* out, const double* xValues, const int& nData)const
{
double a = getParameter("a");
double b = getParameter("b");
......@@ -139,7 +139,7 @@ public:
std::string name()const{return "Cubic";}
void function(double* out, const double* xValues, const int& nData)
void function(double* out, const double* xValues, const int& nData)const
{
double c0 = getParameter("c0");
double c1 = getParameter("c1");
......
......@@ -25,7 +25,7 @@ public:
declareParameter("a1");
}
std::string name()const{return "FunctionFactoryTest_FunctA";}
void function(double* out, const double* xValues, const int& nData){}
void function(double* out, const double* xValues, const int& nData)const{}
void functionDeriv(Jacobian* out, const double* xValues, const int& nData){}
bool hasAttribute(const std::string& attName)const
{
......@@ -68,7 +68,7 @@ public:
std::string name()const{return "FunctionFactoryTest_FunctB";}
void function(double* out, const double* xValues, const int& nData)
void function(double* out, const double* xValues, const int& nData)const
{
}
void functionDeriv(Jacobian* out, const double* xValues, const int& nData)
......@@ -84,7 +84,7 @@ public:
std::string name()const{return "FunctionFactoryTest_CompFunctA";}
void function(double* out, const double* xValues, const int& nData){}
void function(double* out, const double* xValues, const int& nData)const{}
void functionDeriv(Jacobian* out, const double* xValues, const int& nData){}
bool hasAttribute(const std::string& attName)const
{
......@@ -109,7 +109,7 @@ public:
std::string name()const{return "FunctionFactoryTest_CompFunctB";}
void function(double* out, const double* xValues, const int& nData)
void function(double* out, const double* xValues, const int& nData)const
{
}
void functionDeriv(Jacobian* out, const double* xValues, const int& nData)
......
......@@ -21,7 +21,7 @@ public:
std::string name()const{return "IFT_Funct";}
void function(double* out, const double* xValues, const int& nData)
void function(double* out, const double* xValues, const int& nData)const
{
double c0 = getParameter("c0");
double c1 = getParameter("c1");
......
......@@ -20,7 +20,7 @@ public:
declareParameter("c");
}
std::string name()const{return "ParameterReferenceTest_Fun";}
void function(double* out, const double* xValues, const int& nData)
void function(double* out, const double* xValues, const int& nData)const
{
}
};
......
......@@ -20,7 +20,7 @@ public:
declareParameter("sig",1.);
}
std::string name()const{return "ParameterTieTest_Gauss";}
void function(double* out, const double* xValues, const int& nData)
void function(double* out, const double* xValues, const int& nData)const
{
double c = getParameter("cen");
double h = getParameter("hi");
......@@ -87,7 +87,7 @@ public:
declareParameter("b");
}
std::string name()const{return "ParameterTieTest_Linear";}
void function(double* out, const double* xValues, const int& nData)
void function(double* out, const double* xValues, const int& nData)const
{
double a = getParameter("a");
double b = getParameter("b");
......@@ -117,7 +117,7 @@ public:
declareParameter("B1e2Ta_");
}
std::string name()const{return "ParameterTieTest_Nothing";}
void function(double* out, const double* xValues, const int& nData){}
void function(double* out, const double* xValues, const int& nData)const{}
};
class ParameterTieTest : public CxxTest::TestSuite
......
......@@ -194,6 +194,10 @@
Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
>
<File
RelativePath=".\src\BackgroundFunction.cpp"
>
</File>
<File
RelativePath=".\src\BackToBackExponential.cpp"
>
......@@ -308,6 +312,10 @@
Filter="h;hpp;hxx;hm;inl;inc;xsd"
UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
>
<File
RelativePath=".\inc\MantidCurveFitting\BackgroundFunction.h"
>
</File>
<File
RelativePath=".\inc\MantidCurveFitting\BackToBackExponential.h"
>
......
......@@ -66,7 +66,7 @@ namespace Mantid
/// overwrite IFunction base class methods
std::string name()const{return "BackToBackExponential";}
virtual void function(double* out, const double* xValues, const int& nData);
virtual void function(double* out, const double* xValues, const int& nData)const;
virtual void functionDeriv(API::Jacobian* out, const double* xValues, const int& nData);
protected:
......
#ifndef MANTID_CURVEFITTING_BACKGROUNDFUNCTION_H_
#define MANTID_CURVEFITTING_BACKGROUNDFUNCTION_H_
//----------------------------------------------------------------------
// Includes
//----------------------------------------------------------------------
#include "MantidAPI/IBackgroundFunction.h"
#include <boost/shared_array.hpp>
namespace mu
{
class Parser;
}
namespace Mantid
{
namespace CurveFitting
{
/**
A background function. Functions that are intended to be used as backgrounds
should inherit from this class to enable certain features. E.g. querying
@author Roman Tolchenov, Tessella plc
@date 26/04/2010
Copyright &copy; 2007-8 STFC Rutherford Appleton Laboratory
This file is part of Mantid.
Mantid is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3 of the License, or
(at your option) any later version.
Mantid is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see <http://www.gnu.org/licenses/>.
File change history is stored at: <https://svn.mantidproject.org/mantid/trunk/Code/Mantid>
Code Documentation is available at: <http://doxygen.mantidproject.org>
*/
class DLLExport BackgroundFunction : public API::IBackgroundFunction
{
public:
/// Returns the centre of the function, which may be something as simple as the centre of
/// the fitting range in the case of a background function or peak shape function this
/// return value reflects the centre of the peak
double centre()const{return 0.;}
/// Returns the height of the function. For a background function this may return an average
/// height of the background. For a peak function this return value is the height of the peak
double height()const{return 0.;}
/// Sets the parameters such that centre == c
void setCentre(const double c){}
/// Sets the parameters such that height == h
void setHeight(const double h){}
void fit(const std::vector<double>& X,const std::vector<double>& Y);
};
} // namespace CurveFitting
} // namespace Mantid
#endif /*MANTID_CURVEFITTING_BACKGROUNDFUNCTION_H_*/
......@@ -119,7 +119,7 @@ namespace Mantid
/// overwrite IFunction base class methods
std::string name()const{return "Convolution";}
void function(double* out, const double* xValues, const int& nData);
void function(double* out, const double* xValues, const int& nData)const;
//void functionDeriv(API::Jacobian* out, const double* xValues, const int& nData);
/// Add a function.
......
......@@ -69,7 +69,7 @@ namespace Mantid
virtual void calJacobianForCovariance(API::Jacobian* out, const double* xValues, const int& nData);
virtual void setActiveParameter(int i,double value);
virtual double activeParameter(int i)const;
virtual void function(double* out, const double* xValues, const int& nData);
virtual void function(double* out, const double* xValues, const int& nData)const;
virtual void functionDeriv(API::Jacobian* out, const double* xValues, const int& nData);
protected:
......
......@@ -62,7 +62,7 @@ namespace Mantid
//virtual void calJacobianForCovariance(API::Jacobian* out, const double* xValues, const int& nData);
virtual void setActiveParameter(int i,double value);
virtual double activeParameter(int i)const;
virtual void function(double* out, const double* xValues, const int& nData);
virtual void function(double* out, const double* xValues, const int& nData)const;
void constFunction(double* out, const double* xValues, const int& nData) const;
......
......@@ -4,7 +4,7 @@
//----------------------------------------------------------------------
// Includes
//----------------------------------------------------------------------
#include "MantidAPI/Function.h"
#include "MantidCurveFitting/BackgroundFunction.h"
namespace Mantid
{
......@@ -43,7 +43,7 @@ namespace Mantid
File change history is stored at: <https://svn.mantidproject.org/mantid/trunk/Code/Mantid>
Code Documentation is available at: <http://doxygen.mantidproject.org>
*/
class DLLExport LinearBackground : public API::Function
class DLLExport LinearBackground : public BackgroundFunction
{
public:
/// Destructor
......@@ -51,9 +51,11 @@ namespace Mantid
/// overwrite IFunction base class methods
std::string name()const{return "LinearBackground";}
virtual void function(double* out, const double* xValues, const int& nData);
virtual void function(double* out, const double* xValues, const int& nData)const;
virtual void functionDeriv(API::Jacobian* out, const double* xValues, const int& nData);
void fit(const std::vector<double>& X,const std::vector<double>& Y);
protected:
/// overwrite IFunction base class method, which declare function parameters
virtual void init();
......
......@@ -63,7 +63,7 @@ namespace Mantid
/// overwrite IFunction base class methods
std::string name()const{return "Lorentzian";}
virtual void function(double* out, const double* xValues, const int& nData);
virtual void function(double* out, const double* xValues, const int& nData)const;
virtual void functionDeriv(API::Jacobian* out, const double* xValues, const int& nData);
protected:
......
......@@ -52,7 +52,7 @@ namespace Mantid
/// overwrite IFunction base class methods
std::string name()const{return "Quadratic";}
virtual void function(double* out, const double* xValues, const int& nData);
virtual void function(double* out, const double* xValues, const int& nData)const;
virtual void functionDeriv(API::Jacobian* out, const double* xValues, const int& nData);
protected:
......
......@@ -47,8 +47,8 @@ public:
/// overwrite IFunction base class methods
std::string name()const{return "Resolution";}
void function(double* out, const double* xValues, const int& nData);
void functionDeriv(API::Jacobian* out, const double* xValues, const int& nData){}
void function(double* out, const double* xValues, const int& nData)const;
void functionDeriv(API::Jacobian* out, const double* xValues, const int& nData)const{}
/// Returns the number of attributes associated with the function
int nAttributes()const{return 1;}
......
Supports Markdown
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment