// @(#)root/mathmore:$Id$ // Author: L. Moneta Wed Dec 20 17:16:32 2006 /********************************************************************** * * * Copyright (c) 2006 LCG ROOT Math Team, CERN/PH-SFT * * * * * **********************************************************************/ // Implementation file for class GSLSimAnMinimizer #include "Math/GSLSimAnMinimizer.h" #include "Math/WrappedParamFunction.h" #include "Math/Error.h" #include "Math/MinimTransformFunction.h" #include "Math/MultiNumGradFunction.h" // needed to use transformation function #include "Math/FitMethodFunction.h" #include #include namespace ROOT { namespace Math { // GSLSimAnMinimizer implementation GSLSimAnMinimizer::GSLSimAnMinimizer( int /* ROOT::Math::EGSLSimAnMinimizerType type */ ) : BasicMinimizer() { // Constructor implementation : create GSLMultiFit wrapper object SetMaxIterations(100); SetPrintLevel(0); } GSLSimAnMinimizer::~GSLSimAnMinimizer () { } bool GSLSimAnMinimizer::Minimize() { // set initial parameters of the minimizer int debugLevel = PrintLevel(); if (debugLevel >=1 ) std::cout <<"Minimize using GSLSimAnMinimizer " << std::endl; const ROOT::Math::IMultiGenFunction * function = ObjFunction(); if (function == 0) { MATH_ERROR_MSG("GSLSimAnMinimizer::Minimize","Function has not been set"); return false; } // vector of internal values (copied by default) unsigned int npar = NPar(); std::vector xvar; std::vector steps(StepSizes(),StepSizes()+npar); // needed for the transformation MultiNumGradFunction * gradFunc = new MultiNumGradFunction( *function ); gradFunc->SetOwnership(); MinimTransformFunction * trFunc = CreateTransformation(xvar, gradFunc ); // ObjFunction() will return now the new transformed function if (trFunc) { // transform also the step sizes trFunc->InvStepTransformation(X(), StepSizes(), &steps[0]); steps.resize( trFunc->NDim() ); } assert (xvar.size() == steps.size() ); #ifdef DEBUG for (unsigned int i = 0; i < npar ; ++i) { std::cout << "x = " << xvar[i] << " steps " << steps[i] << " x " << X()[i] << std::endl; } std::cout << "f(x) = " << (*ObjFunction())(&xvar.front() ) << std::endl; std::cout << "f(x) not transf = " << (*function)( X() ) << std::endl; if (trFunc) std::cout << "ftrans(x) = " << (*trFunc) (&xvar.front() ) << std::endl; #endif // output vector std::vector xmin(xvar.size() ); int iret = fSolver.Solve(*ObjFunction(), &xvar.front(), &steps.front(), &xmin[0], (debugLevel > 1) ); SetMinValue( (*ObjFunction())(&xmin.front() ) ); SetFinalValues(&xmin.front()); if (debugLevel >=1 ) { if (iret == 0) std::cout << "GSLSimAnMinimizer: Minimum Found" << std::endl; else std::cout << "GSLSimAnMinimizer: Error in solving" << std::endl; int pr = std::cout.precision(18); std::cout << "FVAL = " << MinValue() << std::endl; std::cout.precision(pr); for (unsigned int i = 0; i < NDim(); ++i) std::cout << VariableName(i) << "\t = " << X()[i] << std::endl; } return ( iret == 0) ? true : false; } unsigned int GSLSimAnMinimizer::NCalls() const { // return number of function calls const ROOT::Math::MinimTransformFunction * tfunc = dynamic_cast(ObjFunction()); const ROOT::Math::MultiNumGradFunction * f = 0; if (tfunc) f = dynamic_cast(tfunc->OriginalFunction()); else f = dynamic_cast(ObjFunction()); if (f) return f->NCalls(); return 0; } } // end namespace Math } // end namespace ROOT