Skip to content

Commit

Permalink
Starting to implement (not finished). Refs #8109.
Browse files Browse the repository at this point in the history
  • Loading branch information
wdzhou committed Oct 11, 2013
1 parent 4a4c3b8 commit e9fb804
Show file tree
Hide file tree
Showing 3 changed files with 328 additions and 0 deletions.
Original file line number Diff line number Diff line change
@@ -0,0 +1,87 @@
#ifndef MANTID_CURVEFITTING_FULLPROFPOLYNOMIAL_H_
#define MANTID_CURVEFITTING_FULLPROFPOLYNOMIAL_H_

#include "MantidKernel/System.h"
#include "MantidCurveFitting/BackgroundFunction.h"

namespace Mantid
{
namespace CurveFitting
{

/** FullprofPolynomial : Polynomial background defined in Fullprof
Copyright © 2013 ISIS Rutherford Appleton Laboratory & NScD Oak Ridge National 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://github.com/mantidproject/mantid>
Code Documentation is available at: <http://doxygen.mantidproject.org>
*/
class DLLExport FullprofPolynomial : public BackgroundFunction
{
public:
FullprofPolynomial();
virtual ~FullprofPolynomial();

/// Overwrite IFunction base class
std::string name()const{return "FullprofPolynomial";}

virtual const std::string category() const { return "Background";}

virtual void function1D(double* out, const double* xValues, const size_t nData)const;

virtual void functionDeriv1D(API::Jacobian* out, const double* xValues, const size_t nData);

// virtual void functionLocal(std::vector<double> &out, std::vector<double> xValues) const;

/// Returns the number of attributes associated with the function (polynomial order n)
size_t nAttributes()const{return 1;}

/// Returns a list of attribute names
std::vector<std::string> getAttributeNames()const;

/// Return a value of attribute attName
Attribute getAttribute(const std::string& attName)const;

/// Set a value to attribute attName
void setAttribute(const std::string& attName,const Attribute& );

/// Check if attribute attName exists
bool hasAttribute(const std::string& attName)const;

private:

/// Polynomial order
int m_n;

/// Background origin position
double m_bkpos;

/// Lower x boundary.
double m_StartX;

/// Upper x boundary
double m_EndX;
};

typedef boost::shared_ptr<FullprofPolynomial> FullprofPolynomial_sptr;


} // namespace CurveFitting
} // namespace Mantid

#endif /* MANTID_CURVEFITTING_FULLPROFPOLYNOMIAL_H_ */
213 changes: 213 additions & 0 deletions Code/Mantid/Framework/CurveFitting/src/FullprofPolynomial.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,213 @@
#include "MantidCurveFitting/FullprofPolynomial.h"
#include "MantidAPI/FunctionFactory.h"
#include <boost/lexical_cast.hpp>

namespace Mantid
{
namespace CurveFitting
{

DECLARE_FUNCTION(FullprofPolynomial)

//----------------------------------------------------------------------------------------------
/** Constructor
*/
FullprofPolynomial::FullprofPolynomial():m_n(6), m_bkpos(1.)
{
// Declare first 6th order polynomial as default
for(int i=0; i<=m_n; ++i)
{
std::string parName = "A" + boost::lexical_cast<std::string>(i);
declareParameter(parName);
}
}

//----------------------------------------------------------------------------------------------
/** Destructor
*/
FullprofPolynomial::~FullprofPolynomial()
{
}

//----------------------------------------------------------------------------------------------
/** Function to calcualteFullprofPolynomial
*/
void FullprofPolynomial::function1D(double* out, const double* xValues, const size_t nData)const
{
// FIXME - Not correct
// TODO - Make it correct
/*
x = tof*1.0/bkpos-1.
pow_x = 1.
for i in xrange(order):
y_b += B[i] * pow_x
pow_x = pow_x*x
*/
throw std::runtime_error("Implement ASAP");

// 1. Use a vector for all coefficient
std::vector<double> coeff(m_n+1, 0.0);
for (int i = 0; i < m_n+1; ++i)
coeff[i] = getParameter(i);

// 2. Calculate
for (size_t i = 0; i < nData; ++i)
{
double x = xValues[i];
double temp = coeff[0];
double nx = x;
for (int j = 1; j <= m_n; ++j)
{
temp += coeff[j]*nx;
nx *= x;
}
out[i] = temp;
}

return;
}

//----------------------------------------------------------------------------------------------
/** Function to calcualteFullprofPolynomial based on vector
void FullprofPolynomial::functionLocal(std::vector<double> &out, std::vector<double> xValues) const
{
size_t nData = xValues.size();
if (out.size() > xValues.size())
{
std::stringstream errss;
errss << "Polynomial::functionLocal: input vector out has a larger size ("
<< out.size() << ") than xValues's (" << nData << ").";
throw std::runtime_error(errss.str());
}
for (size_t i = 0; i < nData; ++i)
{
double x = xValues[i];
double temp = getParameter(0);
double nx = x;
for (int j = 1; j <= m_n; ++j)
{
temp += getParameter(j)*nx;
nx *= x;
}
out[i] = temp;
}
return;
}
*/

//----------------------------------------------------------------------------------------------
/** Function to calculate derivative analytically
*/
void FullprofPolynomial::functionDeriv1D(API::Jacobian* out, const double* xValues, const size_t nData)
{
// FIXME - Not correct!
// TODO - Re-do ASAP
throw std::runtime_error("It is not correct!");
for (size_t i = 0; i < nData; i++)
{
double x = xValues[i];
double nx = 1;
for (int j = 0; j <= m_n; ++j)
{
out->set(i, j, nx);
nx *= x;
}
}

return;
}

//----------------------------------------------------------------------------------------------
/** Get Attribute names
* @return A list of attribute names (identical toFullprofPolynomial)
*/
std::vector<std::string> FullprofPolynomial::getAttributeNames()const
{
std::vector<std::string> res;
res.push_back("n");
res.push_back("Bkpos");

return res;
}

//----------------------------------------------------------------------------------------------
/** Get Attribute
* @param attName :: Attribute name. If it is not "n" exception is thrown.
* @return a value of attribute attName
* (identical toFullprofPolynomial)
*/
API::IFunction::Attribute FullprofPolynomial::getAttribute(const std::string& attName)const
{
if (attName == "n")
{
return Attribute(m_n);
}
else if (attName == "Bkpos")
return Attribute(m_bkpos);

throw std::invalid_argument("Polynomial: Unknown attribute " + attName);
}

//----------------------------------------------------------------------------------------------
/** Set Attribute
* @param attName :: The attribute name. If it is not "n" exception is thrown.
* @param att :: An int attribute containing the new value. The value cannot be negative.
* (identical toFullprofPolynomial)
*/
void FullprofPolynomial::setAttribute(const std::string& attName,const API::IFunction::Attribute& att)
{
if (attName == "n")
{
// set theFullprofPolynomial order
int attint = att.asInt();
if (attint < 0)
{
throw std::invalid_argument("Polynomial:FullprofPolynomial order cannot be negative.");
}
else if (attint != 6 && attint != 12)
{
throw std::runtime_error("FullprofPolynomial's order must be either 6 or 12. ");
}
else if (attint != m_n)
{
// Only order is (either 6 or 12) and different from current order
clearAllParameters();

m_n = attint;
for(int i=0; i<=m_n; ++i)
{
std::string parName = "A" + boost::lexical_cast<std::string>(i);
declareParameter(parName);
}
}
}
else if (attName == "Bkpos")
{
// Background original position
m_bkpos = att.asDouble();
}

return;
}

//----------------------------------------------------------------------------------------------
/** Check if attribute attName exists
*/
bool FullprofPolynomial::hasAttribute(const std::string& attName)const
{
bool has = false;
if (attName == "n")
has = true;
else if (attName == "Bkpos")
has = true;

return has;
}


} // namespace CurveFitting
} // namespace Mantid
28 changes: 28 additions & 0 deletions Code/Mantid/Framework/CurveFitting/test/FullprofPolynomialTest.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
#ifndef MANTID_CURVEFITTING_FULLPROFPOLYNOMIALTEST_H_
#define MANTID_CURVEFITTING_FULLPROFPOLYNOMIALTEST_H_

#include <cxxtest/TestSuite.h>

#include "MantidCurveFitting/FullprofPolynomial.h"

using Mantid::CurveFitting::FullprofPolynomial;

class FullprofPolynomialTest : public CxxTest::TestSuite
{
public:
// This pair of boilerplate methods prevent the suite being created statically
// This means the constructor isn't called when running other tests
static FullprofPolynomialTest *createSuite() { return new FullprofPolynomialTest(); }
static void destroySuite( FullprofPolynomialTest *suite ) { delete suite; }


void test_Something()
{
TSM_ASSERT( "You forgot to write a test!", 0);
}


};


#endif /* MANTID_CURVEFITTING_FULLPROFPOLYNOMIALTEST_H_ */

0 comments on commit e9fb804

Please sign in to comment.