def main(): """Toy systematic fitting application. Parses the command line and fits the toys, catching intermediate errors and transforming them to status codes. Status codes: 0: All good. 1: Error in the configuration files. 2: Files missing (configuration or toys). 3: Error configuring physics factories. 4: Error in the event generation. An exception is logged. 5: Input data is inconsistent with previous fits. 128: Uncaught error. An exception is logged. """ parser = argparse.ArgumentParser() parser.add_argument('-v', '--verbose', action='store_true', help="Verbose output") parser.add_argument('--link-from', action='store', type=str, default='', help="Folder to actually store the fit results") parser.add_argument('config', action='store', type=str, nargs='+', help="Configuration files") args = parser.parse_args() if args.verbose: get_logger('analysis').setLevel(1) logger.setLevel(1) else: ROOT.RooMsgService.instance().setGlobalKillBelow(ROOT.RooFit.WARNING) try: exit_status = 0 run(args.config, args.link_from, args.verbose) except KeyError: exit_status = 1 logger.exception("Bad configuration given") except OSError as error: exit_status = 2 logger.error(str(error)) except ValueError: exit_status = 3 logger.exception("Problem configuring physics factories") except RuntimeError as error: exit_status = 4 logger.error("Error in fitting events") except AttributeError as error: exit_status = 5 logger.error("Inconsistent input data -> %s", error) # pylint: disable=W0703 except Exception as error: exit_status = 128 logger.exception('Uncaught exception -> %s', repr(error)) finally: parser.exit(exit_status)
def main(): """Toy generation application. Parses the command line and runs the toys, catching intermediate errors and transforming them to status codes. Status codes: 0: All good. 1: Error in the configuration files. 2: Files missing (configuration or toys). 3: Error configuring physics factories. 4: Error in the event generation. 128: Uncaught error. An exception is logged. """ parser = argparse.ArgumentParser() parser.add_argument('-v', '--verbose', action='store_true', help="Verbose output") parser.add_argument('--link-from', action='store', type=str, default='', help="Folder to actually store the toy files") parser.add_argument('config', action='store', type=str, nargs='+', help="Configuration files") args = parser.parse_args() if args.verbose: get_logger('analysis').setLevel(1) logger.setLevel(1) try: run(args.config, args.link_from) exit_status = 0 except KeyError: exit_status = 1 logger.exception("Bad configuration given") except OSError as error: exit_status = 2 logger.error(str(error)) except ValueError: exit_status = 3 logger.error("Problem configuring physics factories") except RuntimeError as error: exit_status = 4 logger.error("Error in generating events") # pylint: disable=W0703 except Exception as error: exit_status = 128 logger.exception('Uncaught exception -> %s', repr(error)) finally: parser.exit(exit_status)
def main(): """Generator level MC production application. Parses the command line and submits the MC production jobs. Status codes: 0: All good. 1: Missing configuration file. 2: Error in the configuration file. 3: No batch system found. 4: Error in job submission. 128: Uncaught error. An exception is logged. """ parser = argparse.ArgumentParser() parser.add_argument('-v', '--verbose', action='store_true', help="Verbose output") parser.add_argument('--link-from', action='store', type=str, default='', help="Folder to actually store the fit results") parser.add_argument('config', action='store', type=str, nargs='+', help="Configuration files") args = parser.parse_args() if args.verbose: get_logger('analysis.efficiency').setLevel(10) try: exit_status = 0 run(args.config, args.link_from) except OSError: logger.error("Configuration files missing!") exit_status = 1 except KeyError: logger.error("Error in configuration file!") exit_status = 2 except ValueError: logger.error("Cannot find a suitable batch system") exit_status = 3 except RuntimeError: logger.error("Error in job submission") exit_status = 4 # pylint: disable=W0703 except Exception: logger.exception("Uncaught error") exit_status = 128 finally: parser.exit(exit_status)
def main(): """Toy systematic analyzer application. Parses the command line and analyzes the toys, catching intermediate errors and transforming them to status codes. Status codes: 0: All good. 1: Error in the configuration files. 2: Files missing (configuration or toys). 3: Error analyzing toys. 128: Uncaught error. An exception is logged. """ parser = argparse.ArgumentParser() parser.add_argument('-v', '--verbose', action='store_true', help="Verbose output") parser.add_argument('config', action='store', type=str, nargs='+', help="Configuration files") args = parser.parse_args() if args.verbose: get_logger('analysis').setLevel(1) logger.setLevel(1) try: exit_status = 0 run(args.config) except KeyError as error: exit_status = 1 logger.exception("Bad configuration given -> %s", repr(error)) except OSError as error: exit_status = 2 logger.error(str(error)) except RuntimeError as error: exit_status = 3 logger.exception("Error analyzing toys") # pylint: disable=W0703 except Exception as error: exit_status = 128 logger.exception('Uncaught exception -> %s', repr(error)) finally: parser.exit(exit_status)
def main(): """Toy fitting submission application. Parses the command line, configures the toy fitters and submit the jobs, catching intermediate errors and transforming them to status codes. Status codes: 0: All good. 1: Error in the configuration files. 2: Error in preparing the output folders. 3: Conflicting options given. 4: A non-matching configuration file was found in the output. 5: The queue submission command cannot be found. 128: Uncaught error. An exception is logged. """ def flatten(list_, typ_): """Flatten a list.""" return list(sum(list_, typ_)) parser = argparse.ArgumentParser() parser.add_argument('-v', '--verbose', action='store_true', help="Verbose output") parser.add_argument('--link-from', action='store', type=str, help="Folder to actually store the toy files") parser.add_argument('--extend', action='store_true', default=False, help="Extend previous production") parser.add_argument('--overwrite', action='store_true', default=False, help="Overwrite previous production") parser.add_argument('config', action='store', type=str, nargs='+', help="Configuration file") args = parser.parse_args() if args.verbose: get_logger('analysis').setLevel(1) logger.setLevel(1) try: config = _config.load_config(*args.config) # Which type of toy are we running? script_to_run = None submitter = None for toy_type, (toy_class, script_name) in TOY_TYPES.items(): if toy_type in config: script_to_run = script_name submitter = toy_class if submitter is None: raise KeyError("Unknown job type") # Is there something to scan? scan_config = 'scan' in config if scan_config: config_files = [] base_config = _config.unfold_config(config) scan_groups = [] for scan_group in config['scan']: scan_group_dict = {} for key, val_str in scan_group.items(): scan_group_dict[key] = process_scan_val(val_str, scan_group_dict) scan_groups.append(scan_group_dict) # Check lengths if not all(len({len(val) for val in scan_group.values()}) == 1 for scan_group in scan_groups): raise ValueError("Unmatched length in scan parameters") # Build values to scan keys, values = list(zip(*[zip(*scan_group.items()) for scan_group in scan_groups])) keys = flatten(keys, tuple()) for value_tuple in itertools.product(*[zip(*val) for val in values]): values = dict(zip(keys, flatten(value_tuple, tuple()))) temp_config = dict(base_config) del temp_config['scan'] temp_config['name'] = temp_config['name'].format(**values) for key, value in values.items(): temp_config[key] = value logger.debug("Creating configuration %s for scan values -> %s", temp_config['name'], ", ".join('{}: {}'.format(*val) for val in values.items())) # Write temp_file with tempfile.NamedTemporaryFile(delete=False) as file_: file_name = file_.name _config.write_config(_config.fold_config(list(temp_config.items())), file_name) config_files.append(file_name) else: config_files = args.config # pylint: disable=W0702 except: logger.exception("Bad configuration given") parser.exit(1) try: script_to_run = os.path.join(get_global_var('BASE_PATH'), 'toys', script_to_run) for config_file in config_files: submitter(config_files=[config_file], link_from=args.link_from, extend=args.extend, overwrite=args.overwrite, verbose=args.verbose).run(script_to_run, ) if scan_config: os.remove(config_file) exit_status = 0 except KeyError: logger.error("Bad configuration given") exit_status = 1 except OSError as error: logger.error(str(error)) exit_status = 2 except ValueError: logger.error("Conflicting options found") exit_status = 3 except AttributeError: logger.error("Mismatching configuration found") exit_status = 4 except AssertionError: logger.error("Cannot find the queue submission command") exit_status = 5 # pylint: disable=W0703 except Exception as error: exit_status = 128 logger.exception('Uncaught exception -> %s', repr(error)) finally: parser.exit(exit_status)
# -*- coding: utf-8 -*- # ============================================================================= # @file batch_system.py # @author Albert Puig ([email protected]) # @date 31.05.2017 # ============================================================================= """Implementation of different batch systems.""" from __future__ import print_function, division, absolute_import import os import subprocess from collections import OrderedDict from analysis.utils.logging_color import get_logger logger = get_logger('analysis.batch.batch_system') def which(program): """Check the location of the given command. Arguments: program (str): Command to check. Return: str: Path of the program. Returns None if it cannot be found. """ def is_exe(fpath): """Check if path is executable."""
""" from __future__ import print_function, division, absolute_import import argparse import itertools import os import tempfile import analysis.utils.config as _config import analysis.utils.paths as _paths from analysis import get_global_var from analysis.toys.submitter import ToySubmitter from analysis.utils.logging_color import get_logger logger = get_logger('analysis.toys.submit') # Submitter classes # pylint: disable=too-few-public-methods class FitSubmitter(ToySubmitter): """Specialization of ToySubmitter to submit the fitting of toys.""" VALIDATION = {'name': "No name was specified in the config file!", 'fit/nfits': "Number of fits not specified!", # 'fit/nfits-per-job': "Number of fits per job not specified!", # 'fit-model': "No pdfs were specified in the config file!", 'data': "No input data was specified in the config file!"} # pylint: disable=E1101 TOY_PATH_GETTER = staticmethod(_paths.get_toy_fit_path) TOY_CONFIG_PATH_GETTER = staticmethod(_paths.get_toy_fit_config_path)
# @author Albert Puig ([email protected]) # @date 10.04.2017 # ============================================================================= """Manage datasets.""" from __future__ import print_function, division, absolute_import import os import analysis.utils.paths as paths from analysis import get_global_var from analysis.utils.backports import FileNotFoundError from analysis.utils.config import load_config from analysis.utils.exceptions import DataError from analysis.utils.logging_color import get_logger logger = get_logger('analysis.data') def register_file_type(extension, file_type): """Register a file type with a given extension. Return: int: Number of extensions registered with that particular file type. """ if not extension.startswith('.'): extension = "." + extension logger.debug("Registering file type for extension %s -> %s", extension, file_type) get_global_var('FILE_TYPES').update({extension: file_type}) return sum(1 for f_type in get_global_var('FILE_TYPES').values()
# @file converters.py # @author Albert Puig ([email protected]) # @date 13.04.2017 # ============================================================================= """Convert from Pandas to ROOT.""" from __future__ import print_function, division, absolute_import from collections import defaultdict import pandas as pd import ROOT from analysis.utils.root import list_to_rooargset from analysis.utils.logging_color import get_logger logger = get_logger('analysis.data.converters') def pandas_from_dataset(dataset): """Create pandas DataFrame from a RooDataSet. Variable names are used as column names. Arguments: dataset (`ROOT.RooDataSet`): Dataset to convert to pandas. Return: `pandas.DataFrame` """ n_entries = dataset.numEntries()
from __future__ import print_function, division, absolute_import import copy import os import random import string from collections import OrderedDict, defaultdict import yaml import yamlloader from analysis.utils.exceptions import ConfigError from analysis.utils.logging_color import get_logger logger = get_logger('analysis.utils.config') def load_config(*file_names, **options): """Load configuration from YAML files. If more than one is specified, they are loaded in the order given in the function call. Therefore, the latter will override the former if key overlap exists. Currently supported options are: - `root` (str), which determines the node that is considered as root. - `validate` (list), which gets a list of keys to check. If one of these keys is not present, `config.ConfigError` is raised. Additionally, several commands are available to modify the configurations: - The `load` key can be used to load other config files from the
# @date 16.04.2017 # ============================================================================= """Physics utilities.""" from __future__ import print_function, division, absolute_import import traceback from collections import OrderedDict import ROOT from analysis import get_global_var from analysis.utils.config import get_shared_vars, configure_parameter, recursive_dict_copy from analysis.utils.exceptions import ConfigError from analysis.utils.logging_color import get_logger logger = get_logger('analysis.physics') # logger.setLevel(10) # def unfold_ordereddict(ordered_dict): # if isinstance(ordered_dict, OrderedDict): # return {key: unfold(value) for key, value in ordered_dict.items()} # else: # return ordered_dict def register_physics_factories(observable, factories): """Register a physics factory. This model then becomes available to `get_efficiency_model` functions.
""" from __future__ import print_function, division, absolute_import import os import inspect from functools import partial from contextlib import contextmanager import fasteners from analysis import get_global_var from analysis.utils.logging_color import get_logger logger = get_logger('analysis.utils.paths') def _get_path(dirs, extension, name_transformation, name, *args, **kwargs): """Get the path for an object. The path is $BASE_PATH/{'/'.join(dirs)}/{name_transformation(name, args, kwargs)}{extension}. Arguments: dirs (list): Parent directories of the object path. extension (str): Extension of the file (including the dot). Can be empty for directories. name_transformation (Callable, optional): Function to transform the name of the path. name (str): Name of the object. *args (list): Positional arguments to be passed to `name_transformation`. *kwargs (list): Keyword arguments to be passed to `name_transformation`.
# @file tools.py # @author Albert Puig ([email protected]) # @date 14.03.2017 # ============================================================================= """Common tools for managing toys.""" from __future__ import print_function, division, absolute_import import os import contextlib2 import pandas as pd from analysis.utils.logging_color import get_logger from analysis.utils.paths import get_toy_fit_path _logger = get_logger('analysis.toys.tools') def load_toy_fits(*toys, **kwargs): """Load toy fit results. If several files are given, all the tables are merged. Note: The HDFStores are opened and closed. A copy of the data frames is returned. Arguments: *toys (str): Toy names to load. **kwargs (dict): Extra options: + `index` (bool, optional): Index the data frame? Defaults
configuration. """ from __future__ import print_function import argparse import os import pandas as pd import analysis.utils.config as _config import analysis.utils.paths as _paths from analysis.utils.logging_color import get_logger logger = get_logger('analysis.toys.syst_analyze') # Debug def debug(toy_data, _): """Drop to an interactive debugging session. Arguments: toy_data (pd.HDFStore): Toy data to analyze Return: dict: Empty. """ __import__('ipdb').set_trace() return dict()
# ============================================================================= """Randomized toy generators.""" from __future__ import print_function, division, absolute_import from collections import OrderedDict, defaultdict import numpy as np from scipy.stats import poisson from analysis.data.converters import pandas_from_dataset, dataset_from_pandas from analysis.data.mergers import merge_root from analysis.fit.result import FitResult from analysis.utils.logging_color import get_logger from analysis.utils.root import list_to_rooargset, list_to_rooarglist, iterate_roocollection logger = get_logger('analysis.toys.randomizers') class ToyRandomizer(object): """Base class for toy randomizers.""" def __init__(self, model, config=None, acceptance=None): """Configure randomizer. The physics model needs to be extended. In case it isn't, `yield` needs to be specified in `config`. For simultaneous PDFs, `yield` needs to be a dictionary matching categories with their corresponding yield. Arguments: model (`analysis.physics.PhysicsFactory`): Factory used for generation and fitting.
import os import random import string import ROOT import numpy as np import pandas as pd from root_pandas import read_root import formulate from analysis.data.converters import dataset_from_pandas from analysis.utils.logging_color import get_logger from analysis.utils.root import destruct_object, list_to_rooarglist logger = get_logger('analysis.data.loaders') ############################################################################### # Helpers ############################################################################### def _analyze_weight_config(config): """Analyze weight config. Arguments: config (dict): `get_data` configuration. Return: tuple (str, list, list): Name of the total weight variable, weight variables to normalize, weight variables not to normalize.
import numpy as np import pandas as pd from analysis.batch import get_job_id from analysis.data.converters import pandas_from_dataset from analysis.data.hdf import modify_hdf from analysis.physics import configure_model from analysis.physics.factory import SumPhysicsFactory, SimultaneousPhysicsFactory from analysis.utils.config import load_config from analysis.utils.exceptions import ConfigError from analysis.utils.logging_color import get_logger from analysis.utils.paths import get_toy_path, work_on_file from analysis.utils.random_numbers import get_urandom_int from analysis.utils.root import destruct_object, list_to_rooargset logger = get_logger('analysis.toys.generate') def generate(physics_factory, n_events): """Perform generation of toys. Note: If the factory is simultaneous, events are generated in steps. For that reason, the configuration for 'gen/nevents' must be a dictionary of {label -> nevents} keys. Arguments: physics_factory (`analysis.physics.PhysicsFactory`): Physics factory object to get observables, parameters and PDFs from. n_events (dict, int): Number of events to generate.
"""Test imports.""" from __future__ import print_function, division, absolute_import import yaml import yamlloader import pytest import ROOT import analysis.physics as phys import analysis.physics.factory as phys_factory import analysis.physics.pdf_models as pdfs from analysis.utils.logging_color import get_logger from analysis.utils.exceptions import ConfigError get_logger('analysis.physics').setLevel(10) # Define a few factories # pylint: disable=W0223 class MassFactory(phys_factory.PhysicsFactory): """Abstract base class for mass fits. Implements the observables. """ OBSERVABLES = (('mass', 'mass', 5000, 5500, "MeV/c^{2}"), ) class DoubleCBFactory(pdfs.DoubleCBPdfMixin, MassFactory):
# @author Albert Puig ([email protected]) # @date 08.06.2018 # ============================================================================= """Define actions in configuration files.""" from __future__ import print_function, division, absolute_import import ast import operator as op from copy import deepcopy from analysis.utils.logging_color import get_logger import ROOT logger = get_logger('analysis.utils.actions') def action_VAR(name, title, action_params, _): """Load a variable. This action is used for parameters without constraints. If one configuration element is given, the parameter doesn't have limits. If three are given, the last two specify the low and upper limits. Parameter is set to not constant. """ # Take numerical value or load from file if ':' in action_params[0]: # We want to load a fit result from analysis.fit.result import FitResult fit_name, var_name = action_params[0].split(':') result = FitResult.from_yaml_file(fit_name)
# ============================================================================= # @file test_fit.py # @author Albert Puig ([email protected]) # @date 11.07.2017 # ============================================================================= """Test the fit module.""" from __future__ import print_function, division, absolute_import import pytest import ROOT from analysis.fit.result import FitResult from analysis.utils.logging_color import get_logger get_logger('analysis.fit').setLevel(10) @pytest.fixture def fit_result(): """Create a gaussian and fit it.""" # Variables x = ROOT.RooRealVar("x", "x", -10, 10) mu = ROOT.RooRealVar("mu", "mu", 0) sigma = ROOT.RooRealVar("sigma", "sigma", 0.5, 2.5) yield_ = ROOT.RooRealVar("yield", "yield", 50, 10, 100) # PDFs gauss = ROOT.RooGaussian("gauss", "gauss", x, mu, sigma) gauss_ext = ROOT.RooExtendPdf("gauss_ext", "gauss_ext", gauss, yield_) # Dataset dataset = gauss.generate(ROOT.RooArgSet(x), 50)
# @author Albert Puig ([email protected]) # @date 13.04.2017 # ============================================================================= """Deal with HDF files.""" from __future__ import print_function, division, absolute_import import os import subprocess import shutil from contextlib import contextmanager import pandas as pd from analysis.utils.logging_color import get_logger logger = get_logger('analysis.data.hdf') @contextmanager def modify_hdf(file_name, compress=True): """Context manager to process-exclusively open an HDF file and write it to disk on close. Note: This does **NOT** work for threads! The lock applied is an inter-process lock and invokes the fcntl(2) system call. Note: File is compressed on closing. If compression fails, a warning is issued but no error is raised. Arguments:
import functools import itertools import operator import numpy as np import pandas as pd from analysis.utils.logging_color import get_logger from .efficiency import Efficiency # Shortcuts legval = np.polynomial.legendre.legval legint = np.polynomial.legendre.legint logger = get_logger('analysis.efficiency.legendre') ############################################################################### # Utils ############################################################################### def process_range(range_lst): """Process the range, convert to float and manage maths. A few functions are allowed: pi, cos, acos, sin, asin, sqrt. Return: tuple: Range, (low, high). Raise: ValueError: If the range doesn't have two elements or if it cannot
# ============================================================================= """Physics factory classes.""" from __future__ import print_function, division, absolute_import import os import re from collections import OrderedDict import ROOT from analysis.utils.config import configure_parameter from analysis.utils.exceptions import InvalidRequestError from analysis.utils.logging_color import get_logger from analysis.utils.root import execute_and_return_self, list_to_rooargset, list_to_rooarglist logger = get_logger('analysis.physics.factory') # The base class class BaseFactory(object): """Physics analysis factory. Implements the basic skeleton. """ OBSERVABLES = OrderedDict() PARAMETERS = None MANDATORY_PARAMETERS = {} PARAMETER_DEFAULTS = OrderedDict()
from __future__ import print_function, division, absolute_import import os import argparse import matplotlib.pyplot as plt from analysis import get_global_var from analysis.data import get_data from analysis.utils.logging_color import get_logger import analysis.utils.config as _config import analysis.utils.paths as _paths from analysis.efficiency import get_efficiency_model_class, load_efficiency_model logger = get_logger('analysis.efficiency.calculate_efficiency') # Register plot path get_efficiency_plot_path = _paths.register_path( 'efficiency_plot', ['data_files', 'efficiency'], 'eps', lambda name, args, kwargs: name + '_{}'.format(kwargs['var'])) def run(config_files, link_from): """Run the script. If the efficiency file exists, only the plots are remade. Arguments: config_files (list[str]): Path to the configuration files. link_from (str): Path to link the results from.
#!/usr/bin/env python # -*- coding: utf-8 -*- # ============================================================================= # @file data.py # @author Albert Puig ([email protected]) # @date 16.01.2017 # ============================================================================= """Fit-related utils.""" from __future__ import print_function, division, absolute_import import pandas as pd from analysis.utils.logging_color import get_logger logger = get_logger('analysis.utils.fit') def fit_parameters_to_dict(parameters): """Extract the important information of fit parameters. This allows to store uncertainties in pandas dataframes. For each parameter `par` in `parameters` the following entries are stored: - `{par}`: value. - `{par}_err_hesse`: parabolic error (`getError` method). - `{par}_err_plus`: upper error (`getErrorHi`). - `{par}_err_minus`: signed lower error (`getErrorLo`). Arguments: parameters (list[`ROOT.RooRealVar`]): Fit parameters
# @date 28.09.2017 # ============================================================================= """Produce generator-level MC for acceptance calculations.""" from __future__ import print_function, division, absolute_import import argparse import os from math import ceil import analysis.utils.config as _config import analysis.utils.paths as _paths from analysis.batch import get_batch_system from analysis.mc.gauss import get_gauss_version, get_gaudirun_options, get_db_tags from analysis.utils.logging_color import get_logger logger = get_logger('analysis.efficiency.gen_level') SCRIPT = """#!{shell} ##################################### {header} ##################################### echo "------------------------------------------------------------------------" echo "Job started on" `date` echo "------------------------------------------------------------------------" set -e if [ -f $HOME/.localrc ]; then source $HOME/.localrc fi source LbLogin.sh -c x86_64-slc6-gcc48-opt source SetupProject.sh Gauss {gauss_version} seed=`echo ${jobid_var} | cut -d'.' -f1`
""" from __future__ import print_function, division, absolute_import import os from analysis import get_global_var from analysis.utils.config import load_config, ConfigError, unfold_config from analysis.utils.paths import get_efficiency_path, get_acceptance_path from analysis.utils.logging_color import get_logger from .legendre import _EFFICIENCY_MODELS as _LEG_EFFICIENCY_MODELS from .acceptance import Acceptance logger = get_logger('analysis.efficiency') def register_efficiency_model(model_name, model_class): """Register an efficiency model. This model then becomes available to `get_efficiency_model` functions. Arguments: model_name (str): Name of the model. model_class (`Efficiency`): Efficiency model to register. Return: int: Number of registered efficiency models """
from analysis.utils.monitoring import memory_usage from analysis.utils.random_numbers import get_urandom_int from analysis.data.hdf import modify_hdf from analysis.physics import configure_model from analysis.efficiency import get_acceptance from analysis.fit import fit from analysis.fit.result import FitResult from analysis.batch import get_job_id from analysis.toys import get_randomizer import analysis.utils.paths as _paths import analysis.utils.config as _config import analysis.utils.root as _root import ROOT logger = get_logger('analysis.toys.syst') def run(config_files, link_from, verbose): """Run the script. Run a generate/fit sequence as many times as requested. Arguments: config_files (list[str]): Path to the configuration files. link_from (str): Path to link the results from. verbose (bool): Give verbose output? Raise: OSError: If the configuration file or some other input does not exist. AttributeError: If the input data are incompatible with a previous fit.
# -*- coding: utf-8 -*- # ============================================================================= # @file __init__.py # @author Albert Puig ([email protected]) # @date 11.01.2017 # ============================================================================= """Common utilities.""" from __future__ import print_function, division, absolute_import import inspect from analysis import get_global_var from analysis.utils.logging_color import get_logger from analysis.utils import actions as _actions logger = get_logger('analysis.utils') def register_config_action(name, action_function): """Register a config action keyword. The action gets four parameters: - The name of the parameter - The title of the parameter - The parameter configuration - The list of shared vars. Arguments: name (str): Name of the action. action_function (Callable): Parameter config action.
import analysis.utils.paths as _paths import analysis.utils.root as _root from analysis.batch import get_job_id from analysis.data import get_data from analysis.data.converters import dataset_from_pandas from analysis.data.hdf import modify_hdf from analysis.efficiency import get_acceptance from analysis.fit import fit from analysis.fit.result import FitResult from analysis.physics import configure_model from analysis.utils.exceptions import ConfigError from analysis.utils.logging_color import get_logger from analysis.utils.monitoring import memory_usage from analysis.utils.random_numbers import get_urandom_int logger = get_logger('analysis.toys.fit') def get_datasets(data_frames, acceptance, fit_models): """Build the datasets from the input toys. If an acceptance is specified, events are selected using accept-reject. Logic regarding the poisson variation of yields is as follows: - If the fit model is extended, the yields of the individual data sets are varied as randomly following a poisson distribution. - If the fit model is not extended, the yields of the individual data set are exactly the number of events given in the configuration. Note: Proper handling of poissonian variations is not fool proof. If datasets contain a