00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030 #include "TFitter.h"
00031 #include "TMVA/MinuitFitter.h"
00032 #include "TMVA/MinuitWrapper.h"
00033 #include "TMVA/Interval.h"
00034 #include "TMVA/Timer.h"
00035
00036 ClassImp(TMVA::MinuitFitter)
00037
00038
00039 TMVA::MinuitFitter::MinuitFitter( IFitterTarget& target,
00040 const TString& name,
00041 std::vector<TMVA::Interval*>& ranges,
00042 const TString& theOption )
00043 : TMVA::FitterBase( target, name, ranges, theOption ),
00044 TMVA::IFitterTarget( )
00045 {
00046
00047
00048
00049 DeclareOptions();
00050 ParseOptions();
00051
00052 Init();
00053 }
00054
00055
00056 TMVA::MinuitFitter::~MinuitFitter( )
00057 {
00058
00059 delete fMinWrap;
00060 }
00061
00062
00063 void TMVA::MinuitFitter::DeclareOptions()
00064 {
00065
00066
00067 DeclareOptionRef(fErrorLevel = 1, "ErrorLevel", "TMinuit: error level: 0.5=logL fit, 1=chi-squared fit" );
00068 DeclareOptionRef(fPrintLevel = -1, "PrintLevel", "TMinuit: output level: -1=least, 0, +1=all garbage" );
00069 DeclareOptionRef(fFitStrategy = 2, "FitStrategy", "TMinuit: fit strategy: 2=best" );
00070 DeclareOptionRef(fPrintWarnings = kFALSE, "PrintWarnings", "TMinuit: suppress warnings" );
00071 DeclareOptionRef(fUseImprove = kTRUE, "UseImprove", "TMinuit: use IMPROVE" );
00072 DeclareOptionRef(fUseMinos = kTRUE, "UseMinos", "TMinuit: use MINOS" );
00073 DeclareOptionRef(fBatch = kFALSE, "SetBatch", "TMinuit: use batch mode" );
00074 DeclareOptionRef(fMaxCalls = 1000, "MaxCalls", "TMinuit: approximate maximum number of function calls" );
00075 DeclareOptionRef(fTolerance = 0.1, "Tolerance", "TMinuit: tolerance to the function value at the minimum" );
00076 }
00077
00078
00079 void TMVA::MinuitFitter::Init()
00080 {
00081
00082 Double_t args[10];
00083
00084
00085 if (!fBatch) Log() << kINFO << "<MinuitFitter> Init " << Endl;
00086
00087
00088 Timer timer;
00089
00090
00091
00092
00093
00094
00095 fMinWrap = new MinuitWrapper( fFitterTarget, 2*GetNpars() );
00096
00097
00098 args[0] = fPrintLevel;
00099 fMinWrap->ExecuteCommand( "SET PRINTOUT", args, 1 );
00100
00101 if (fBatch) fMinWrap->ExecuteCommand( "SET BAT", args, 0 );
00102
00103
00104 fMinWrap->Clear();
00105
00106
00107 args[0] = fErrorLevel;
00108 fMinWrap->ExecuteCommand( "SET ERR", args, 1 );
00109
00110
00111 if (!fPrintWarnings) fMinWrap->ExecuteCommand( "SET NOWARNINGS", args, 0 );
00112
00113
00114 args[0] = fFitStrategy;
00115 fMinWrap->ExecuteCommand( "SET STRATEGY", args, 1 );
00116 }
00117
00118
00119 Double_t TMVA::MinuitFitter::Run( std::vector<Double_t>& pars )
00120 {
00121
00122
00123
00124 Double_t args[10];
00125
00126
00127 if ( !fBatch ) Log() << kINFO << "<MinuitFitter> Fitting, please be patient ... " << Endl;
00128
00129
00130 if ((Int_t)pars.size() != GetNpars())
00131 Log() << kFATAL << "<Run> Mismatch in number of parameters: (a)"
00132 << GetNpars() << " != " << pars.size() << Endl;
00133
00134
00135 Timer* timer = 0;
00136 if (!fBatch) timer = new Timer();
00137
00138
00139 for (Int_t ipar=0; ipar<fNpars; ipar++) {
00140 fMinWrap->SetParameter( ipar, Form( "Par%i",ipar ),
00141 pars[ipar], fRanges[ipar]->GetWidth()/100.0,
00142 fRanges[ipar]->GetMin(), fRanges[ipar]->GetMax() );
00143 if (fRanges[ipar]->GetWidth() == 0.0) fMinWrap->FixParameter( ipar );
00144 }
00145
00146
00147
00148
00149 args[0] = fMaxCalls;
00150 args[1] = fTolerance;
00151
00152
00153 fMinWrap->ExecuteCommand( "MIGrad", args, 2 );
00154
00155
00156 if (fUseImprove) fMinWrap->ExecuteCommand( "IMProve", args, 0 );
00157
00158
00159 if (fUseMinos) {
00160 args[0] = 500;
00161 fMinWrap->ExecuteCommand( "MINOs", args, 1 );
00162 }
00163
00164
00165 Double_t chi2;
00166 Double_t edm;
00167 Double_t errdef;
00168 Int_t nvpar;
00169 Int_t nparx;
00170 fMinWrap->GetStats( chi2, edm, errdef, nvpar, nparx );
00171
00172
00173 if (GetNpars() != nparx) {
00174 Log() << kFATAL << "<Run> Mismatch in number of parameters: "
00175 << GetNpars() << " != " << nparx << Endl;
00176 }
00177
00178
00179 for (Int_t ipar=0; ipar<GetNpars(); ipar++) {
00180 Double_t errp, errm, errsym, globcor, currVal, currErr;
00181 fMinWrap->GetParameter( ipar, currVal, currErr );
00182 pars[ipar] = currVal;
00183 fMinWrap->GetErrors( ipar, errp, errm, errsym, globcor );
00184 }
00185
00186
00187
00188
00189 if (!fBatch) {
00190 Log() << kINFO << "Elapsed time: " << timer->GetElapsedTime()
00191 << " " << Endl;
00192 delete timer;
00193 }
00194
00195 fMinWrap->Clear();
00196
00197 return chi2;
00198 }
00199
00200
00201 Double_t TMVA::MinuitFitter::EstimatorFunction( std::vector<Double_t>& pars )
00202 {
00203
00204 return Run( pars );
00205 }
00206
00207