#include "sopnamsp.h" #include "machdefs.h" #include #include #include #include #include #include #include "fioarr.h" #include "ntuple.h" #include "Minuit2/FunctionMinimum.h" #include "Minuit2/MnMigrad.h" #include "Minuit2/MnUserParameters.h" #include "Minuit2/MnPrint.h" #include "Minuit2/MnMinos.h" #include "Minuit2/MinosError.h" #include "Minuit2/FCNBase.h" using namespace ROOT::Minuit2; //-------------------------------------------------- namespace ROOT { namespace Minuit2 { class MyFCN : public FCNBase { public: MyFCN(TVector& FreqMHz,TVector& V,TVector& EV); void InitFit(MnUserParameters& upar); double Func(double fr,const vector& par) const; double operator()(const vector& par) const; double Up(void) const {return 1.;} void SetNu0(double nu0Mhz) {_nu0 = nu0Mhz;} //protected: double _nu0; mutable int _ndata; TVector _F; TVector _V; TVector _EV; }; } } // namespace ROOT + Minuit2 //-------------------------------------------------- int main(int narg,char *arg[]) { int nslicemax = -1; if(narg<=1) { cout<<"cmvgsmcfit cubefile.ppf [nslicemax]"<2) nslicemax = atoi(arg[2]); cout<<"Fitting "< Cube; pis>>PPFNameTag("cube")>>Cube; TVector Freq; pis>>PPFNameTag("freq")>>Freq; const int nvar = 8; const char *vname[nvar] = {"x2r","ok","ph","th","v0","vn","A","N"}; NTuple nt(nvar,vname); double xnt[nvar]; for(int i=0;i0 && j>=nslicemax) break; } cout<<"nfit = "<& FreqMHz,TVector& V,TVector& EV) : _F(FreqMHz,false), _V(V,false), _EV(EV,false) { if(_F.Size()==0 || _F.Size()!=_V.Size() || _F.Size()!=_EV.Size()) throw SzMismatchError("MyFCN::MyFCN_Error: incompatible F / V / EV sizes"); _nu0 = _F(0); _ndata =_V.Size(); } void MyFCN::InitFit(MnUserParameters& upar) { int n = _F.Size() - 1; double a = _V(0); double ni = log(_V(n)/a) / log(_F(n)/_nu0); upar.Add("A",a,a/50.); upar.Add("N",ni,fabs(ni/50.)); } double MyFCN::Func(double fr,const vector& par) const // v = A*(nu/nu0)^N { double f = par[0]*pow(fr/_nu0,par[1]); return f; } double MyFCN::operator()(const vector& par) const { double xi2 = 0.; _ndata = 0; for(int i=0;i<_V.Size();i++) { double e2 = _EV(i)*_EV(i); if(e2<=0.) continue; double v = _V(i); double f = Func(_F(i),par); xi2 += (v-f)*(v-f)/e2; _ndata++; } //cout<<"par: "<