[RooFit] Integral

I have a fit which is a sum of signal and background.

RooRealVar x("x","x",1,1.04);
RooDataHist data("data","dataset with x",x,mass);     // mass is a histo
RooRealVar mean ("mean","mean",1.02,1.01,1.03);

RooRealVar sigmabw("sigmabw","sigmabw",0.0043,0,0.01);
RooRealVar sigmag("sigmag","sigmag",0.01,0,0.1);
RooGaussian signal("signal","signal",x,mean,sigmag) ;

RooRealVar parbkg("parexp","parexp",0.1,-482,482);
RooExponential bkg("bkg","bkg",x,parbkg);

RooRealVar fsig("fsig","signal fraction",0,1);
RooAddPdf model("model","model",RooArgList(signal,bkg),fsig);
model.fitTo(data,PrintLevel(-1));

// plot
RooPlot* frame = x.frame();
data.plotOn(frame);
model.plotOn(frame,ProjWData(data));
model.plotOn(frame,Components("signal"),LineColor(kDashed));
model.plotOn(frame,Components("bkg"),LineStyle(kDashed));

I would like to get three integrals:

  1. Integral of of my fit (model)
  2. Integral of signal (gauss)
  3. Integral of background (exponent)

But, what is important that I don’t want to normalize them! I just need pure numbers of events under each curve. I’ve experimented with method “createIntegral” but I couldn’t manage to take unnormaized signal and background.

Thanks in advance

Nobody has an idea?

Hi Jimmy,

I would like to get three integrals:

  1. Integral of of my fit (model)
  2. Integral of signal (gauss)
  3. Integral of background (exponent)

But, what is important that I don’t want to normalize them! I just need pure numbers of
events under each curve. I’ve experimented with method “createIntegral” but I couldn’t <
manage to take unnormaized signal and background.

I think what you really want is an extended maximum likelihood fit, which not only
fits the shape but also the number of events. In roofit you can do that like this

RooRealVar nsig(“nsig”,“signal events”,0,10000);
RooRealVar nbkg(“nbkg”,“signal background events”,0,10000);
RooAddPdf model(“model”,“model”,RooArgList(signal,bkg),RooArgList(nsig,nbkg));
model.fitTo(data,PrintLevel(-1),Extended());

This fit will give you directly the first two numbers you want (with errors!). The total number under the curve is by construction equal to the number of events in the dataset

Wouter

Thank you, it works (nsig.getVal(), nbkg.getVal()).

Here I suppose that one should use “data.numEntries(1)”?
It works, but not perfectly.
Number of event under the fit to model is equal to sum of signal and background. Both of these numbers can be non-integer or even negative value. From my experience with RooFit, it doesn’t look like they sum together to number of events, although to something very close to this number. They are rounded somehow, somewhere…
Maybe it is not important in most cases, but in principle this is not the same ,and can bias further calculations.

Hi,

I am puzzled by some of your statements.

It works, but not perfectly

How do you measure this?

Both of these numbers can be non-integer or even negative value.

That doesn’t prevent the sum from being a positive integer number
(for non-extended ML fits).

For extended ML fits a terms is added to the likelihood that constrains the the expected number of events (=nsig+nbkg) to the observed number of events, taking into account the statistical uncertaintly. Since nsig and nbkg also influence the shape of the fit, it is possible that shape information and events count information are not in perfect agreement. The ML fit will effective find the minimum somewhere in between which may indeed lead to nsig+nbkg not being exactly ndata.

Note that this is not a flaw in RooFit but just the property of the (extended) ML estimator… Although an (extended) ML estimator has many desirable properties, it is not guaranteed to be unbiased at finite N.

Maybe it is not important in most cases, but in principle this is not the same ,and can bias further calculations

I would like to empasize that what RooFit does not do any rounding or make any approximations. Any bias you see is likely the property of the ML estimator.

Wouter