Source code for pyhf.optimize.opt_minuit

"""MINUIT Optimizer Backend."""

import iminuit
import logging
import numpy as np

log = logging.getLogger(__name__)


[docs]class minuit_optimizer(object): """MINUIT Optimizer Backend."""
[docs] def __init__(self, verbose=False, ncall=10000, errordef=1, steps=1000): """ Create MINUIT Optimizer. Args: verbose (`bool`): print verbose output during minimization """ self.verbose = 0 self.ncall = ncall self.errordef = errordef self.steps = steps
def _make_minuit( self, objective, data, pdf, init_pars, init_bounds, fixed_vals=None ): def f(pars): result = objective(pars, data, pdf) logpdf = result[0] return logpdf parnames = ['p{}'.format(i) for i in range(len(init_pars))] kw = {'limit_p{}'.format(i): b for i, b in enumerate(init_bounds)} initvals = {'p{}'.format(i): v for i, v in enumerate(init_pars)} step_sizes = { 'error_p{}'.format(i): (b[1] - b[0]) / float(self.steps) for i, b in enumerate(init_bounds) } fixed_vals = fixed_vals or [] constraints = {} for index, value in fixed_vals: constraints = {'fix_p{}'.format(index): True} initvals['p{}'.format(index)] = value kwargs = {} for d in [kw, constraints, initvals, step_sizes]: kwargs.update(**d) mm = iminuit.Minuit( f, print_level=1 if self.verbose else 0, errordef=1, use_array_call=True, forced_parameters=parnames, **kwargs ) return mm
[docs] def minimize( self, objective, data, pdf, init_pars, par_bounds, fixed_vals=None, return_fitted_val=False, return_uncertainties=False, ): """ Find Function Parameters that minimize the Objective. Returns: bestfit parameters """ mm = self._make_minuit(objective, data, pdf, init_pars, par_bounds, fixed_vals) result = mm.migrad(ncall=self.ncall) assert result if return_uncertainties: bestfit_pars = np.asarray([(v, mm.errors[k]) for k, v in mm.values.items()]) else: bestfit_pars = np.asarray([v for k, v in mm.values.items()]) bestfit_value = mm.fval if return_fitted_val: return bestfit_pars, bestfit_value return bestfit_pars