and i have a question about generating gauss constraints terms likelihoods to add then as RooAddition.
I have a fitter code which performs the simultaneous fits avoiding the fitTo, but using the CreateNLL of a model relative to a dataset to fit.
In the past to add constraints i was able to manipulate the log-likelihood discovering parameters floating it was dependent on and then generate my own RooGaussian constraint using RooNLLVar.
It seems like RooNLLVar is removed. I wonder how i can still generate a constraint penalty term following a summation of negative log-likelihood terms bypassing the need of a dataset (or empty dataset).
Could anyone help to understand how to still enable creating a negative LL term for a gaussian constrain on a floating parameter of a pre-exiting NLL?
I see i can use ROOT.RooFit.Detail.RooNLLVarNew with ROOT 6/36 but my conda environment on lxplus is limited up to 6.34.04. What is the way to do it on that version?
indeed the RooNLLVar was removed (actually, made private) in ROOT 6.34. The release notes unfortunately don’t mention how to migrate, so we better call on @jonas to give directions for upgrading.
True, the 6.34 release notes didn’t mention the removal, but the deprecation was announced with 6.32:
Can you share the code where you modified the RooNLLVar in the past? Then I understand better what kind of constraint you mean and can make a clear recommendation.
I tried to navigate back my code in C++ and i see i was using RooConstraintSum, but i was somewhat assuming i could have created a RooNLLVar to add in a RooAddition to a model.createNLL(data).
I have now converted the code to python from C++ which reads like this.
# those are a list created with a model.createNLL( data) for each split i do in the fit,
all_likelihoods = [likelihoods[l] for l in likelihoods.keys()]
floating_vars_inlikelihood = []
for l in all_likelihoods :
vars = l.getVariables()
for v in vars:
if not( v.isConstant()):
floating_vars_inlikelihood.append(v.GetName())
floating_vars_inlikelihood = list(set(floating_vars_inlikelihood))
gconstspdfs = []
gconstrvars = []
for _ in floating_vars_inlikelihood:
logger.info(f"In Likelihood param-Name floating = {_}")
gauss_constr = Pool.GetOneDGaussConstraint(_ )
param_constr = Pool.GetPar( _)
if gauss_constr is not None :
logger.warning(f"Adding 1D - gaussian constraint on parameter {_} in all-likelihood")
if param_constr is None :
raise ValueError("Cannot get parameter floating in likelihood from ")
param_constr = Pool.GetPar( _)
gconstspdfs.append( gauss_constr)
gconstrvars.append( Pool.GetParameter())
else:
pass
if len( gconstspdfs) != 0 :
all_constraints_ll = ROOT.RooConstraintSum("constraintSumOneD", "constraintSumOneD", gconstspdfs, gconstrvars)
all_likelihoods.append( all_constraints_ll)
In my code what i do is that i have a class ParameterPool (Pool) , which on demand generate for a give var a var_mean and var_sigma constants which are then used in a RooGaussian() which is exactly the pdf retrieved for a given parameter constrained 1D by Pool.GetPar( _)
In practice, i have a list of floating parameters in my main likelihood function, and those parameters are the variable of a gaussian with a mean and sigma value. Those gaussians and the variable are traced in lists and then passed in a RooConstraintSum which i assume that it can then be added to other model.createNLL outputs, e.g. RooConstraintSum is generating from the gaussian the associated likelihood penalty term?
It would be great if you could confirm this is a the legitimate approach to manually add 1-D constraints to the fit on a parameter the likelihood depend on.
In general the question si whether RooConstraintSum( gaussians, variables) are a good -nLL term to add to existing NLL terms, or i need to get the gaussian constraint and make a parabola function to add in the NLL and whether for constraints, since RooNLLVar was the only kind of variable which could be constructed without a dataset input, is something i should still use or try to use it.
Actually i was rechecking my code, and indeed i never used RooNLLVar for gaussian constraints, i was just creating Gaussians with var_mean, var_sigma and
RooGaussian( var, var_mean, var_sigma)
which then were ending up in a RooConstraintSum object which was then added to the NLL of the datasets + models ensuring that the LL created was dependent on var.
I guess i don’t need at all RooNLLVar at this point but i am just wondering if this is ultimately what fitTo does.
Indeed, you don’t need RooNLLVar for this kind of 1D constraints, and adding a RooConstraintSum to a likelihood created by createNLL() is completely fine. Although the canonical way of achieving this is to pass the list of Gaussians to the ExternalConstraints() argument of RooAbsPdf::createNLL(). Would that work for you too? The advantage is that the resulting NLL will be more computationally optimized, because createNLL() has the overview on everything in the final likelihood and can do more holistic optimizations.
and then i do this for n-pdfs mapping to n-datasets (so i am not using RooSimultaneousPdf),
do i double/triple/4x- count the constraints applied if the mygausspdf_to_constraint_a_parameter or a list of gaussians are passed to each call ?
This is the reason i wanted to separate the LL terms of pdfs-datasets addition and then navigate the overall NLL to find the parameters it depends on only once and count only once the constraints in a RooConstraintsSum( [ gaussians]). The part i am not sure is whether RooConstraintsSum using gaussians as inputs are then adding a LL penalty with a parabola ( e.g. a gaussian constraint to the NLL)