ATLAS Offline Software
Functions
GenericMonitoringTool Namespace Reference

Functions

def _invalidName (flags, name)
 Check if name is an allowed histogram/branch name. More...
 
def _alias (varname)
 Generate an alias for a set of variables. More...
 
def _validateOptions (user, default)
 Validate user inputs for "opt" argument of defineHistogram. More...
 
def _options (opt)
 Generate dictionary entries for opt strings. More...
 
def defineHistogram (flags, varname, type='TH1F', path=None, title=None, weight=None, xbins=100, xmin=0, xmax=1, xlabels=None, ybins=None, ymin=None, ymax=None, ylabels=None, zmin=None, zmax=None, zlabels=None, opt=None, convention=None, cutmask=None, treedef=None, merge=None)
 Generate histogram definition string for the GenericMonitoringTool.Histograms property. More...
 
def defineTree (flags, varname, treedef, path=None, title=None, opt='', convention=None, cutmask=None)
 Generate tree definition string for the GenericMonitoringTool.Histograms property. More...
 

Function Documentation

◆ _alias()

def GenericMonitoringTool._alias (   varname)
private

Generate an alias for a set of variables.

A helper function is useful for this operation, since it is used both by the module function defineHistogram, as well as by the GenericMonitoringArray defineHistogram member function.

Parameters
varnameunparsed
Returns
varList, alias

Definition at line 199 of file GenericMonitoringTool.py.

199 def _alias(varname):
200  variableAliasSplit = varname.split(';')
201  varList = [v.strip() for v in variableAliasSplit[0].split(',')]
202  if len(variableAliasSplit)==1:
203  return varList, '_vs_'.join(reversed(varList))
204  elif len(variableAliasSplit)==2:
205  return varList, variableAliasSplit[1]
206  else:
207  message = 'Invalid variable or alias for {}. Histogram(s) not defined.'
208  log.warning(message.format(varname))
209  return None, None
210 
211 

◆ _invalidName()

def GenericMonitoringTool._invalidName (   flags,
  name 
)
private

Check if name is an allowed histogram/branch name.

Certain characers are best avoided in ROOT histogram names as it makes interactive use awkward. Also there are additional constraints from OH and MDA archiving for online running (ATR-15173).

Parameters
flagsconfiguration flags
namestring to check
Returns
set of forbidden characters found

Definition at line 185 of file GenericMonitoringTool.py.

185 def _invalidName(flags, name):
186  blocklist = '/\\'
187  if flags.Common.isOnline:
188  blocklist += '=,:.()'
189  return set(name).intersection(blocklist)
190 
191 

◆ _options()

def GenericMonitoringTool._options (   opt)
private

Generate dictionary entries for opt strings.

Parameters
optstring or dictionary specifying type
Returns
dictionary full of options

Definition at line 238 of file GenericMonitoringTool.py.

238 def _options(opt):
239  # Set the default dictionary of options
240  settings = {
241  'Sumw2': False, # store sum of squares of weights
242  'kLBNHistoryDepth': 0, # length of lumiblock history
243  'kAddBinsDynamically': False, # add new bins if fill is outside axis range
244  'kRebinAxes': False, # increase axis range without adding new bins
245  'kCanRebin': False, # allow all axes to be rebinned
246  'kVec': False, # add content to each bin from each element of a vector
247  'kVecUO': False, # same as above, but use 0th(last) element for underflow(overflow)
248  'kCumulative': False, # fill bin of monitored object's value, and every bin below it
249  'kLive': 0, # plot only the last N lumiblocks on y_vs_LB plots
250  'kAlwaysCreate': False # create the histogram, even if it is empty
251  }
252  if opt is None:
253  # If no options are provided, skip any further checks.
254  pass
255  elif isinstance(opt, dict):
256  # If the user provides a partial dictionary, update the default with user's.
257  _validateOptions(opt, settings) # check validity of user's options
258  settings.update(opt) # update the default dictionary
259  elif isinstance(opt, str) and len(opt)>0:
260  # If the user provides a comma- or space-separated string of options.
261  settings = _options (opt.replace(',',' ').split())
262 
263  elif isinstance(opt,str):
264  # empty string case
265  pass
266  elif isinstance(opt, list):
267  # process each item in list
268  unknown = []
269  for o in opt:
270  kv = o.split('=', maxsplit=1)
271  key = kv[0]
272  if len(kv)==2:
273  value = False if kv[1]=='False' else int(kv[1]) # only bool and int supported
274  else:
275  value = True
276  if key in settings:
277  assert(type(settings[key])==type(value)) # ensure same type as in defaults
278  settings[key] = value
279  else:
280  unknown.append(key)
281 
282  assert len(unknown)==0, f'Unknown option(s) provided: {", ".join(unknown)}.'
283  else:
284  raise ValueError("Unknown opt type")
285  return settings
286 
287 

◆ _validateOptions()

def GenericMonitoringTool._validateOptions (   user,
  default 
)
private

Validate user inputs for "opt" argument of defineHistogram.

Check that the user-provided option for a specific "opt" argument exists in the default dictionary, and that it has the expected type.

Parameters
userthe option dictionary provided by the user
defaultthe default dictionary of options

Definition at line 218 of file GenericMonitoringTool.py.

218 def _validateOptions(user, default):
219  for key, userVal in user.items():
220  # (1) Check that the requested key exists
221  assert key in default,\
222  f'Unknown option {key} provided. Choices are [{", ".join(default)}].'
223  # (2) Check that the provided type is correct
224  userType = type(userVal)
225  defaultVal = default[key]
226  defaultType = type(defaultVal)
227  if isinstance(userVal, bool) or isinstance(defaultVal, bool):
228  assert isinstance(userVal, bool) and isinstance(defaultVal, bool),\
229  f'{key} provided {userType}, expected bool.'
230  else:
231  assert isinstance(defaultVal, userType),\
232  f'{key} provided {userType}, expected {defaultType}'
233 
234 

◆ defineHistogram()

def GenericMonitoringTool.defineHistogram (   flags,
  varname,
  type = 'TH1F',
  path = None,
  title = None,
  weight = None,
  xbins = 100,
  xmin = 0,
  xmax = 1,
  xlabels = None,
  ybins = None,
  ymin = None,
  ymax = None,
  ylabels = None,
  zmin = None,
  zmax = None,
  zlabels = None,
  opt = None,
  convention = None,
  cutmask = None,
  treedef = None,
  merge = None 
)

Generate histogram definition string for the GenericMonitoringTool.Histograms property.

For full details see the GenericMonitoringTool documentation.

Parameters
flagsconfiguration flags object
varnameone (1D) or two (2D) variable names separated by comma optionally give histogram name by appending ";" plus the name
typehistogram type
pathtop-level histogram directory (e.g. EXPERT, SHIFT, etc.)
titleHistogram title and optional axis title (same syntax as in TH constructor)
weightName of the variable containing the fill weight
cutmaskName of the boolean-castable variable that determines if the plot is filled
optString or dictionary of histogram options (see _options())
treedefInternal use only. Use defineTree() method.
xlabelsList of x bin labels.
ylabelsList of y bin labels.
zlabelsList of x bin labels.
mergeMerge method to use for object, if not default. Possible algorithms for offline DQM are given in https://twiki.cern.ch/twiki/bin/view/Atlas/DQMergeAlgs

Definition at line 306 of file GenericMonitoringTool.py.

306 def defineHistogram(flags, varname, type='TH1F', path=None,
307  title=None, weight=None,
308  xbins=100, xmin=0, xmax=1, xlabels=None,
309  ybins=None, ymin=None, ymax=None, ylabels=None,
310  zmin=None, zmax=None, zlabels=None,
311  opt=None, convention=None, cutmask=None,
312  treedef=None, merge=None):
313 
314  # All of these fields default to an empty string
315  stringSettingsKeys = ['xvar', 'yvar', 'zvar', 'type', 'path', 'title', 'weight',
316  'cutMask', 'convention', 'alias', 'treeDef', 'merge']
317  # All of these fileds default to 0
318  numberSettingsKeys = ['xbins', 'xmin', 'xmax', 'ybins', 'ymin', 'ymax', 'zbins',
319  'zmin', 'zmax']
320  # All of these fields default to an empty array
321  arraySettingsKeys = ['allvars', 'xlabels', 'xarray', 'ylabels', 'yarray', 'zlabels']
322  # Initialize a dictionary with all possible fields
323  settings = dict((key, '') for key in stringSettingsKeys)
324  settings.update(dict((key, 0.0) for key in numberSettingsKeys))
325  settings.update(dict((key, []) for key in arraySettingsKeys))
326 
327  # Alias
328  varList, alias = _alias(varname)
329  if alias is None or alias.strip() == '':
330  log.warning(f'Unable to define histogram using definition "{varname}" since we cannot determine its name.')
331  return ''
332 
333  invalid = _invalidName(flags, alias)
334  if invalid:
335  log.warning('%s is not a valid histogram name. Illegal characters: %s',
336  alias, ' '.join(invalid))
337  return ''
338 
339  settings['alias'] = alias
340 
341  # Variable names
342  nVars = len(varList)
343  if nVars>0:
344  settings['xvar'] = varList[0]
345  if nVars>1:
346  settings['yvar'] = varList[1]
347  if nVars>2:
348  settings['zvar'] = varList[2]
349  settings['allvars'] = varList
350 
351  # Type
352  if flags.Common.isOnline and type in ['TTree']:
353  log.warning('Object %s of type %s is not supported for online running and '
354  'will not be added.', varname, type)
355  return ''
356 
357  # Allowed histogram dimensions
358  if type.startswith('TH1'):
359  dims = {1}
360  elif type.startswith('TH2'):
361  dims = {2}
362  elif type=='TProfile':
363  dims = {2}
364  elif type=='TProfile2D':
365  dims = {3}
366  elif type=='TEfficiency':
367  dims = {2, 3}
368 
369  assert type=='TTree' or nVars in dims,\
370  f'Number of monitored variables {varList} for "{path}/{alias}" '\
371  f'does not match histogram dimension for {type}'
372 
373  settings['type'] = type
374 
375  # Path
376  if path is None:
377  path = ''
378  settings['path'] = path
379 
380  # Title
381  if title is None:
382  title = varname
383  settings['title'] = title
384 
385  # Weight
386  if weight is not None:
387  settings['weight'] = weight
388 
389  # Cutmask
390  if cutmask is not None:
391  settings['cutMask'] = cutmask
392 
393  # Output path naming convention
394  if convention is not None:
395  settings['convention'] = convention
396 
397  # Bin counts and ranges
398  # Possible types allowed for bin counts
399  binTypes = (int, list, tuple)
400 
401  # X axis count and range
402  assert isinstance(xbins, binTypes),'xbins argument must be int, list, or tuple'
403  if isinstance(xbins, int): # equal x bin widths
404  settings['xbins'], settings['xarray'] = xbins, []
405  else: # x bin edges are set explicitly
406  settings['xbins'], settings['xarray'] = len(xbins)-1, xbins
407  settings['xmin'] = xmin
408  settings['xmax'] = xmax
409 
410  # Y axis count and range
411  if ybins is not None:
412  assert isinstance(ybins, binTypes),'ybins argument must be int, list, or tuple'
413  if isinstance(ybins, int): # equal y bin widths
414  settings['ybins'], settings['yarray'] = ybins, []
415  else: # y bin edges are set explicitly
416  settings['ybins'], settings['yarray'] = len(ybins)-1, ybins
417  if ymin is not None:
418  settings['ymin'] = ymin
419  if ymax is not None:
420  settings['ymax'] = ymax
421 
422  # Z axis count and range
423  if zmin is not None:
424  settings['zmin'] = zmin
425  if zmax is not None:
426  settings['zmax'] = zmax
427 
428  # Then, parse the [xyz]label arguments
429  if xlabels is not None and len(xlabels)>0:
430  assert isinstance(xlabels, (list, tuple)),'xlabels must be list or tuple'
431  settings['xbins'] = len(xlabels)
432  settings['xlabels'] = xlabels
433  if ylabels is not None and len(ylabels)>0:
434  assert isinstance(ylabels, (list, tuple)),'ylabels must be list or tuple'
435  settings['ybins'] = len(ylabels)
436  settings['ylabels'] = ylabels
437  # if user did not specify ymin and ymax, set it here, as cannot have ymin=ymax=0
438  if ymin is None: settings["ymin"] = 0
439  if ymax is None: settings["ymax"] = settings["ymin"]+1
440  if zlabels is not None and len(zlabels)>0:
441  assert isinstance(zlabels, (list, tuple)),'zlabels must be list or tuple'
442  settings['zlabels'] = zlabels
443 
444  # Tree branches
445  if treedef is not None:
446  assert type=='TTree','cannot define tree branches for a non-TTree object'
447  settings['treeDef'] = treedef
448 
449  # Add all other options
450  settings.update(_options(opt))
451 
452  # some things need merging
453  if ((settings['kAddBinsDynamically'] or settings['kRebinAxes'] or settings['kCanRebin'])
454  and (not flags.Common.isOnline and 'OFFLINE' in settings['convention'])):
455  if merge is None:
456  log.warning(f'Merge method for {alias} is not specified but needs to be "merge" due to histogram definition; overriding for your convenience')
457  merge = 'merge'
458 
459  # merge method
460  if merge is not None:
461  assert type not in ['TEfficiency', 'TTree', 'TGraph'],'only default merge defined for non-histogram objects'
462  settings['merge'] = merge
463 
464  # LB histograms always need to be published online (ADHI-4947)
465  if settings['kLBNHistoryDepth']>0 and flags.Common.isOnline:
466  settings['kAlwaysCreate'] = True
467  log.debug('Setting kAlwaysCreate for lumiblock histogram "%s"', varname)
468 
469  # Check that kLBNHistoryDepth and kLive are both non-negative
470  assert settings['kLBNHistoryDepth']>=0, f'Histogram "{alias}" has invalid kLBNHistoryDepth.'
471  assert settings['kLive']>=0, f'Histogram "{alias}" has invalid kLive.'
472  # kLBNHistoryDepth and kLive options are mutually exclusive. User may not specify both.
473  assert settings['kLBNHistoryDepth']==0 or settings['kLive']==0,\
474  f'Cannot use both kLBNHistoryDepth and kLive for histogram {alias}.'
475  # kLive histograms are only available for Online monitoring.
476  assert settings['kLive']==0 or flags.Common.isOnline,\
477  f'Cannot use kLive with offline histogram {alias}.'
478 
479  return json.dumps(settings)
480 
481 

◆ defineTree()

def GenericMonitoringTool.defineTree (   flags,
  varname,
  treedef,
  path = None,
  title = None,
  opt = '',
  convention = None,
  cutmask = None 
)

Generate tree definition string for the GenericMonitoringTool.Histograms property.

Convenience tool for

For full details see the GenericMonitoringTool documentation.

Parameters
flagsconfiguration flags object
varnameat least one variable name (more than one should be separated by comma); optionally give the name of the tree by appending ";" plus the tree name
treedefTTree branch definition string. Looks like the standard TTree definition (see https://root.cern.ch/doc/master/classTTree.html#addcolumnoffundamentaltypes). In fact if only scalars are given, it is exactly the same as you would use to define the TTree directly: "varA/F:varB/I:...". Vectors can be defined by giving "vector<int>", etc., instead of "I".
pathtop-level histogram directory (e.g. EXPERT, SHIFT, etc.)
titleHistogram title and optional axis title (same syntax as in TH constructor)
cutmaskName of the boolean-castable variable that determines if the plot is filled
optTTree options (none currently)
conventionExpert option for how the objects are placed in ROOT

Definition at line 498 of file GenericMonitoringTool.py.

498 def defineTree(flags, varname, treedef, path=None, title=None,
499  opt='', convention=None,
500  cutmask=None):
501  return defineHistogram(flags, varname, type='TTree', path=path, title=title,
502  treedef=treedef, opt=opt, convention=convention,
503  cutmask=cutmask)
GenericMonitoringTool._invalidName
def _invalidName(flags, name)
Check if name is an allowed histogram/branch name.
Definition: GenericMonitoringTool.py:185
GenericMonitoringTool._options
def _options(opt)
Generate dictionary entries for opt strings.
Definition: GenericMonitoringTool.py:238
intersection
std::vector< std::string > intersection(std::vector< std::string > &v1, std::vector< std::string > &v2)
Definition: compareFlatTrees.cxx:25
python.CaloAddPedShiftConfig.type
type
Definition: CaloAddPedShiftConfig.py:42
GenericMonitoringTool._alias
def _alias(varname)
Generate an alias for a set of variables.
Definition: GenericMonitoringTool.py:199
CxxUtils::set
constexpr std::enable_if_t< is_bitmask_v< E >, E & > set(E &lhs, E rhs)
Convenience function to set bits in a class enum bitmask.
Definition: bitmask.h:232
TCS::join
std::string join(const std::vector< std::string > &v, const char c=',')
Definition: Trigger/TrigT1/L1Topo/L1TopoCommon/Root/StringUtils.cxx:10
python.CaloAddPedShiftConfig.int
int
Definition: CaloAddPedShiftConfig.py:45
GenericMonitoringTool.defineTree
def defineTree(flags, varname, treedef, path=None, title=None, opt='', convention=None, cutmask=None)
Generate tree definition string for the GenericMonitoringTool.Histograms property.
Definition: GenericMonitoringTool.py:498
GenericMonitoringTool.defineHistogram
def defineHistogram(flags, varname, type='TH1F', path=None, title=None, weight=None, xbins=100, xmin=0, xmax=1, xlabels=None, ybins=None, ymin=None, ymax=None, ylabels=None, zmin=None, zmax=None, zlabels=None, opt=None, convention=None, cutmask=None, treedef=None, merge=None)
Generate histogram definition string for the GenericMonitoringTool.Histograms property.
Definition: GenericMonitoringTool.py:306
GenericMonitoringTool._validateOptions
def _validateOptions(user, default)
Validate user inputs for "opt" argument of defineHistogram.
Definition: GenericMonitoringTool.py:218
Trk::split
@ split
Definition: LayerMaterialProperties.h:38