158 lines
5.4 KiB
C++
158 lines
5.4 KiB
C++
/***************************************************************************
|
|
|
|
mn2test.cpp
|
|
|
|
Author: Andreas Suter
|
|
e-mail: andreas.suter@psi.ch
|
|
|
|
$Id$
|
|
|
|
***************************************************************************/
|
|
|
|
/***************************************************************************
|
|
* Copyright (C) 2007 by Andreas Suter *
|
|
* andreas.suter@psi.ch *
|
|
* *
|
|
* This program 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 2 of the License, or *
|
|
* (at your option) any later version. *
|
|
* *
|
|
* This program 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, write to the *
|
|
* Free Software Foundation, Inc., *
|
|
* 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
|
|
***************************************************************************/
|
|
|
|
#include <stdlib.h>
|
|
#include <math.h>
|
|
|
|
#include <iostream>
|
|
#include <vector>
|
|
|
|
#include "Minuit2/FunctionMinimum.h"
|
|
#include "Minuit2/MnUserParameters.h"
|
|
#include "Minuit2/MnMinimize.h"
|
|
#include "Minuit2/MnMinos.h"
|
|
|
|
#include "PGlobalChiSquare.h"
|
|
|
|
#include "mn2test.h"
|
|
|
|
using namespace ROOT::Minuit2;
|
|
|
|
//----------------------------------------------------------------------------
|
|
/**
|
|
* <p>generates data for testing
|
|
* model = ampl * exp(-lambda * t), where ampl is depending on the run, but
|
|
* not lambda
|
|
*/
|
|
void generateData(PRunList &data)
|
|
{
|
|
PRun run;
|
|
const unsigned int length = 100;
|
|
double value;
|
|
|
|
for (unsigned int i=0; i<2; i++) { // run loop
|
|
for (unsigned int j=0; j<length; j++) { // data loop
|
|
run.fTime.push_back((double)j/(double)length);
|
|
value = (2*i+10)*exp(-1.7*(double)j/(double)length);
|
|
value += 2.0*sqrt(value)*((double)random()/(double)RAND_MAX-0.5);
|
|
run.fValue.push_back(value);
|
|
run.fError.push_back(sqrt(value/4.0));
|
|
}
|
|
data.push_back(run);
|
|
|
|
// clean up
|
|
run.fTime.clear();
|
|
run.fValue.clear();
|
|
run.fError.clear();
|
|
}
|
|
}
|
|
|
|
//----------------------------------------------------------------------------
|
|
int main(int argc, char *argv[])
|
|
{
|
|
if (argc || argv);
|
|
|
|
int success = 1;
|
|
|
|
PRunList runs;
|
|
generateData(runs);
|
|
|
|
unsigned int max = 25;
|
|
if (runs[0].fTime.size() < max)
|
|
max = runs[0].fTime.size();
|
|
for (unsigned int i=0; i<runs.size(); i++) { // run loop
|
|
std::cout << std::endl << "run " << i;
|
|
for (unsigned int j=0; j<max; j++) { // data loop
|
|
std::cout << std::endl << runs[i].fTime[j] << ", " << runs[i].fValue[j] << ", " << runs[i].fError[j];
|
|
}
|
|
std::cout << std::endl;
|
|
}
|
|
|
|
PGlobalChiSquare chi2(runs); // chi2 object derived from ROOT::Minuit2::FCNBase
|
|
|
|
// create parameters ---------------------------------
|
|
MnUserParameters upar;
|
|
|
|
// model = ampl_i * exp(-lambda * t), i = run no.
|
|
upar.Add("ampl1", 10.0, 1.0); // ampl1
|
|
upar.Add("ampl2", 12.0, 1.0); // ampl2
|
|
upar.Add("lambda", 0.1, 0.01); // lambda
|
|
|
|
// create minimizer ---------------------------------
|
|
MnMinimize minimize(chi2, upar);
|
|
|
|
// minimize
|
|
FunctionMinimum min = minimize();
|
|
|
|
if (min.IsValid()) {
|
|
std::cout << std::endl << "minimize (MIGRAD/SIMPLEX) found minimum ...";
|
|
} else {
|
|
std::cout << std::endl << "minimize (MIGRAD/SIMPLEX) failed to find minimum ...";
|
|
}
|
|
std::cout << std::endl << "Chi2 = " << min.Fval()
|
|
<< ", NDF = " << 2*runs[0].fTime.size()-3
|
|
<< ", Chi2r = " << min.Fval()/((double)(2*runs[0].fTime.size()-3)) << std::endl;
|
|
|
|
// make minos analysis
|
|
MnMinos minos(chi2, min);
|
|
|
|
// 1-sigma MINOS errors
|
|
std::pair<double, double> e0 = minos(0);
|
|
std::pair<double, double> e1 = minos(1);
|
|
std::pair<double, double> e2 = minos(2);
|
|
|
|
// print out parameters
|
|
unsigned int i=0;
|
|
std::cout << std::endl << "1-sigma minos errors:" << std::endl;
|
|
i=0;
|
|
std::cout << std::endl << upar.Name(i) << ": "
|
|
<< min.UserState().Value(i) << " "
|
|
<< e0.first << " "
|
|
<< e0.second;
|
|
i++;
|
|
std::cout << std::endl << upar.Name(i) << ": "
|
|
<< min.UserState().Value(i) << " "
|
|
<< e1.first << " "
|
|
<< e1.second;
|
|
i++;
|
|
std::cout << std::endl << upar.Name(i) << ": "
|
|
<< min.UserState().Value(i) << " "
|
|
<< e2.first << " "
|
|
<< e2.second;
|
|
|
|
std::cout << std::endl << std::endl;
|
|
|
|
// clean up
|
|
runs.clear();
|
|
|
|
return success;
|
|
}
|