Hi @jonas ,
Thanks a lot for the reply! I’m trying to use xm
and dm
as fundamental variables because my signal peaks in these two variables. The model
pdf in the test script is used to describe a background which peaks in xm+dm
only. I guess model
, as a product of tPdf
and xPdf
, is still a valid pdf for xm
and dm
? It seems working in this test script:
#!/usr/bin/env python3
from ROOT import gROOT, TFile, TCanvas, RooAbsReal, RooArgSet, RooWorkspace, RooFit
def test():
w = RooWorkspace('w')
w.factory('xm[670,650,720]')
w.factory('dm[900,875,995]')
w.factory('expr::bm("xm+dm",xm,dm)')
# w.factory('Gaussian::tPdf(bm,mean[1620,1615,1625],sigma[5,0.1,25])')
# w.factory('CrystalBall::tPdf(bm,mean[1620,1615,1625],sigma[5.,0.1,10],sigma,aL[3.06,0.1,9],nL[2.43,0.1,9],aR[4.37,0.1,12],nR[8.08,0.1,12])')
w.factory('Hypatia2::tPdf(bm,l[-4.,-9,-0.6],zeta[0,0,10],fb[0],sigma[15.,0.1,20],mean[1620,1615,1625],aL[100,0.1,200],nL[2.43,0.1,10],aR[100,0.1,200],nR[8.0,0.1,10])')
w.factory('Chebychev::xPdf(xm, {a1p[0.9,0,1],a2p[0.1,0,0.5]})')
w.factory('PROD::model(tPdf, xPdf)')
w['zeta'].setConstant(True)
w['aL'].setConstant(True)
w['nL'].setConstant(True)
w['aR'].setConstant(True)
w['nR'].setConstant(True)
xm = w['xm']
dm = w['dm']
bm = w['bm']
tPdf = w.pdf('tPdf')
model = w.pdf('model')
obs = RooArgSet(xm,dm)
data = model.generate(obs, 50000)
bmv = data.addColumn(bm)
# tPdf.fitTo(data)
# bframe = bmv.frame(RooFit.Bins(100), RooFit.Range(1560,1680))
# data.plotOn(bframe)
#
# # tPdf.plotOn(bframe)
# tPdf.plotOn(bframe, RooFit.ProjWData(data))
# # tPdf.plotOn(bframe,RooFit.Normalization(data.sumEntries(), RooAbsReal.NumEvent))
# # tPdf.plotOn(bframe,RooFit.Normalization(1.0, RooAbsReal.RelativeExpected))
# # tPdf.plotOn(bframe, RooFit.Normalization(1., RooAbsReal.Relative))
# bframe.Draw()
w['a1p'].setVal(0.5)
w['a2p'].setVal(0.2)
w['mean'].setVal(1624)
w['sigma'].setVal(9)
w['l'].setVal(-1.5)
rf = model.fitTo(data,Save=True)
rf.Print("v")
c1 = TCanvas()
c1.Divide(3)
c1.cd(1)
xm = w.var('xm')
xframe = xm.frame()
data.plotOn(xframe)
model.plotOn(xframe)
xframe.Draw()
c1.cd(2)
dm = w.var('dm')
dframe = dm.frame()
data.plotOn(dframe)
model.plotOn(dframe)
dframe.Draw()
c1.cd(3)
bframe = bmv.frame(Bins=100,Range=(1560,1680))
data.plotOn(bframe)
model.plotOn(bframe, RooFit.Normalization(2.e-19, RooAbsReal.Relative))
bframe.Draw()
c1.Update()
a = input('wait...')
if __name__ == '__main__':
test()
The distribution I can get is
The normalization for
xm
and
dm
are the default but for
bm
I have to scale it by 2.e-19 to get it close to data.
Also thanks for the tips and the work behind them. They helps a lot to make my codes clear.