Loading [MathJax]/extensions/tex2jax.js
ATLAS Offline Software
All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Macros Modules Pages
Public Member Functions | Static Public Member Functions | Public Attributes | List of all members
python.OutputAnalysisConfig.OutputAnalysisConfig Class Reference
Inheritance diagram for python.OutputAnalysisConfig.OutputAnalysisConfig:
Collaboration diagram for python.OutputAnalysisConfig.OutputAnalysisConfig:

Public Member Functions

def __init__ (self)
 
def createOutputAlgs (self, config, name, vars, isMet=False)
 
def makeAlgs (self, config)
 
def createSelectionFlagBranches (self, config)
 
def makeSelectionSummaryAlg (self, config, containerName, selectionName)
 

Static Public Member Functions

def branchSortOrder (rule)
 

Public Attributes

 vars
 
 varsOnlyForMC
 
 metVars
 
 truthMetVars
 

Detailed Description

the ConfigBlock for the MET configuration

Definition at line 10 of file OutputAnalysisConfig.py.

Constructor & Destructor Documentation

◆ __init__()

def python.OutputAnalysisConfig.OutputAnalysisConfig.__init__ (   self)

Definition at line 13 of file OutputAnalysisConfig.py.

13  def __init__ (self) :
14  super (OutputAnalysisConfig, self).__init__ ()
15  self.addOption ('postfix', '', type=str,
16  info="a postfix to apply to decorations and algorithm names. "
17  "Typically not needed here.")
18  self.addOption ('vars', [], type=None,
19  info="a list of mappings (list of strings) between containers and "
20  "decorations to output branches. The default is [] (empty list).")
21  self.addOption ('varsOnlyForMC', [], type=None,
22  info="same as vars, but for MC-only variables so as to avoid a "
23  "crash when running on data. The default is [] (empty list).")
24  self.addOption ('metVars', [], type=None,
25  info="a list of mappings (list of strings) between containers "
26  "and decorations to output branches. Specficially for MET "
27  "variables, where only the final MET term is retained. "
28  "The default is [] (empty list).")
29  self.addOption ('truthMetVars', [], type=None,
30  info="a list of mappings (list of strings) between containers "
31  "and decorations to output branches for truth MET. "
32  "The default is [] (empty list).")
33  self.addOption ('containers', {}, type=None,
34  info="a dictionary mapping prefixes (key) to container names "
35  "(values) to be used when saving to the output tree. Branches "
36  "are then of the form prefix_decoration.")
37  self.addOption ('containersOnlyForMC', {}, type=None,
38  info="same as containers, but for MC-only containers so as to avoid "
39  "a crash when running on data.")
40  self.addOption ('containersOnlyForDSIDs', {}, type=None,
41  info="specify which DSIDs are allowed to produce a given container. "
42  "This works like 'onlyForDSIDs': pass a list of DSIDs or regexps.")
43  self.addOption ('treeName', 'analysis', type=str,
44  info="name of the output TTree to save. The default is analysis.")
45  self.addOption ('streamName', 'ANALYSIS', type=str,
46  info="name of the output stream to save the tree in. "
47  "The default is ANALYSIS.")
48  self.addOption ('metTermName', 'Final', type=str,
49  info="the name (string) of the MET term to save, turning the MET "
50  "container into a single object. The default is 'Final'.")
51  self.addOption ('truthMetTermName', 'NonInt', type=str,
52  info="the name (string) of the truth MET term to save, turning the MET "
53  "container into a single object. The default is 'NonInt'.")
54  # TODO: add info strng
55  self.addOption ('storeSelectionFlags', True, type=bool,
56  info="")
57  # TODO: add info strng
58  self.addOption ('selectionFlagPrefix', 'select', type=str,
59  info="")
60  self.addOption ('commands', [], type=None,
61  info="a list of strings containing commands (regexp strings "
62  "prefaced by the keywords enable or disable) to turn on/off the "
63  "writing of branches to the output ntuple. The default is None "
64  "(no modification to the scheduled output branches).")
65  self.addOption ('commandsOnlyForDSIDs', {}, type=None,
66  info="a dictionary with individual DSIDs as keys, and a list of strings "
67  "like for the 'commands' option as items. These 'commands' will only be run "
68  "for the corresponding DSID.")
69  self.addOption ('alwaysAddNosys', False, type=bool,
70  info="If set to True, all branches will be given a systematics suffix, "
71  "even if they have no systematics (beyond the nominal).")
72 

Member Function Documentation

◆ branchSortOrder()

def python.OutputAnalysisConfig.OutputAnalysisConfig.branchSortOrder (   rule)
static

Definition at line 74 of file OutputAnalysisConfig.py.

74  def branchSortOrder (rule):
75  return rule.split('->')[1].strip()
76 

◆ createOutputAlgs()

def python.OutputAnalysisConfig.OutputAnalysisConfig.createOutputAlgs (   self,
  config,
  name,
  vars,
  isMet = False 
)
A helper function to create output algorithm

Definition at line 77 of file OutputAnalysisConfig.py.

77  def createOutputAlgs (self, config, name, vars, isMet=False):
78  """A helper function to create output algorithm"""
79  alg = config.createAlgorithm('CP::AsgxAODMetNTupleMakerAlg' if isMet else 'CP::AsgxAODNTupleMakerAlg', name)
80  alg.TreeName = self.treeName
81  alg.RootStreamName = self.streamName
82  branchList = list(vars)
83  branchList.sort(key=self.branchSortOrder)
84  branchList_nosys = [branch for branch in branchList if "%SYS%" not in branch]
85  branchList_sys = [branch for branch in branchList if "%SYS%" in branch]
86  alg.Branches = branchList_nosys + branchList_sys
87  return alg
88 

◆ createSelectionFlagBranches()

def python.OutputAnalysisConfig.OutputAnalysisConfig.createSelectionFlagBranches (   self,
  config 
)
For each container and for each selection, create a single pass variable in output NTuple,
which aggregates all the selections flag of the given selection. For example, this can include
pT, eta selections, some object ID selection, overlap removal, etc.
The goal is to have only one flag per object and working point in the output NTuple.

Definition at line 222 of file OutputAnalysisConfig.py.

222  def createSelectionFlagBranches(self, config):
223  """
224  For each container and for each selection, create a single pass variable in output NTuple,
225  which aggregates all the selections flag of the given selection. For example, this can include
226  pT, eta selections, some object ID selection, overlap removal, etc.
227  The goal is to have only one flag per object and working point in the output NTuple.
228  """
229  originalContainersSeen = []
230  for prefix in self.containers.keys() :
231  outputContainerName = self.containers[prefix]
232  containerName = config.getOutputContainerOrigin(outputContainerName)
233  if containerName in originalContainersSeen:
234  continue
235  else:
236  originalContainersSeen.append(containerName)
237 
238  # EventInfo is one obvious example of a container that has no object selections
239  if containerName == 'EventInfo':
240  continue
241 
242  selectionNames = config.getSelectionNames(containerName)
243  for selectionName in selectionNames:
244  # skip default selection
245  if selectionName == '':
246  continue
247  self.makeSelectionSummaryAlg(config, containerName, selectionName)
248 

◆ makeAlgs()

def python.OutputAnalysisConfig.OutputAnalysisConfig.makeAlgs (   self,
  config 
)

Definition at line 89 of file OutputAnalysisConfig.py.

89  def makeAlgs (self, config) :
90 
91  log = logging.getLogger('OutputAnalysisConfig')
92 
93  self.vars = set(self.vars)
94  self.varsOnlyForMC = set(self.varsOnlyForMC)
95  self.metVars = set(self.metVars)
96  self.truthMetVars = set(self.truthMetVars)
97 
98  # merge the MC-specific branches and containers into the main list/dictionary only if we are not running on data
99  if config.dataType() is not DataType.Data:
100  self.vars |= self.varsOnlyForMC
101 
102  # protect 'containers' against being overwritten
103  # find overlapping keys
104  overlapping_keys = set(self.containers.keys()).intersection(self.containersOnlyForMC.keys())
105  if overlapping_keys:
106  # convert the set of overlapping keys to a list of strings for the message (represents the empty string too!)
107  keys_message = [repr(key) for key in overlapping_keys]
108  raise KeyError(f"containersOnlyForMC would overwrite the following container keys: {', '.join(keys_message)}")
109 
110  # move items in self.containersOnlyForMC to self.containers
111  self.containers.update(self.containersOnlyForMC)
112  # clear the dictionary to avoid overlapping key error during the second pass
113  self.containersOnlyForMC.clear()
114 
115  # now filter the containers depending on DSIDs
116  for container,dsid_filters in self.containersOnlyForDSIDs.items():
117  if container not in self.containers:
118  log.warning(f"Skipping unrecognised container {container} for DSID-filtering in OutputAnalysisConfig...")
119  continue
120  if not filter_dsids (dsid_filters, config):
121  # if current DSID is not allowed for this container, remove it
122  self.containers.pop (container)
123 
124  if self.storeSelectionFlags:
125  self.createSelectionFlagBranches(config)
126 
127  outputConfigs = {}
128  for prefix in self.containers.keys() :
129  containerName = self.containers[prefix]
130  outputDict = config.getOutputVars (containerName)
131  for outputName in outputDict :
132  outputConfig = copy.deepcopy (outputDict[outputName])
133  if containerName != outputConfig.origContainerName :
134  outputConfig.outputContainerName = containerName + '_%SYS%'
135  else :
136  outputConfig.outputContainerName = config.readName (containerName)
137  outputConfigs[prefix + outputName] = outputConfig
138 
139  # check for DSID-specific commands
140  for dsid, dsid_commands in self.commandsOnlyForDSIDs.items():
141  if filter_dsids([dsid], config):
142  self.commands += dsid_commands
143 
144  for command in self.commands :
145  words = command.split (' ')
146  if len (words) == 0 :
147  raise ValueError ('received empty command for "commands" option')
148  if words[0] == 'enable' :
149  if len (words) != 2 :
150  raise ValueError ('enable takes exactly one argument: ' + command)
151  used = False
152  for name in outputConfigs :
153  if re.match (words[1], name) :
154  outputConfigs[name].enabled = True
155  used = True
156  if not used and config.dataType() is not DataType.Data:
157  raise KeyError ('unknown branch pattern for enable: ' + words[1])
158  elif words[0] == 'disable' :
159  if len (words) != 2 :
160  raise ValueError ('disable takes exactly one argument: ' + command)
161  used = False
162  for name in outputConfigs :
163  if re.match (words[1], name) :
164  outputConfigs[name].enabled = False
165  used = True
166  if not used and config.dataType() is not DataType.Data:
167  raise KeyError ('unknown branch pattern for disable: ' + words[1])
168  else :
169  raise KeyError ('unknown command for "commands" option: ' + words[0])
170 
171  autoVars = set()
172  autoMetVars = set()
173  autoTruthMetVars = set()
174  for outputName in outputConfigs :
175  outputConfig = outputConfigs[outputName]
176  if outputConfig.enabled :
177  if config.isMetContainer (outputConfig.origContainerName):
178  if "Truth" in outputConfig.origContainerName:
179  myVars = autoTruthMetVars
180  else:
181  myVars = autoMetVars
182  else :
183  myVars = autoVars
184  if outputConfig.noSys :
185  outputConfig.outputContainerName = outputConfig.outputContainerName.replace ('%SYS%', 'NOSYS')
186  outputConfig.variableName = outputConfig.variableName.replace ('%SYS%', 'NOSYS')
187  if self.alwaysAddNosys :
188  outputName += "_NOSYS"
189  else :
190  outputName += '_%SYS%'
191  myVars.add(f"{outputConfig.outputContainerName}.{outputConfig.variableName} -> {outputName}")
192 
193  if self.postfix:
194  postfix = self.postfix
195  else:
196  postfix = self.treeName
197 
198  # Add an ntuple dumper algorithm:
199  treeMaker = config.createAlgorithm( 'CP::TreeMakerAlg', f'TreeMaker{postfix}' )
200  treeMaker.TreeName = self.treeName
201  treeMaker.RootStreamName = self.streamName
202  # the auto-flush setting still needs to be figured out
203  #treeMaker.TreeAutoFlush = 0
204 
205  if self.vars or autoVars:
206  ntupleMaker = self.createOutputAlgs(config, f'NTupleMaker{postfix}', self.vars | autoVars)
207 
208  if self.metVars or autoMetVars:
209  ntupleMaker = self.createOutputAlgs(config, f'MetNTupleMaker{postfix}', self.metVars | autoMetVars, isMet=True)
210  ntupleMaker.termName = self.metTermName
211 
212  if config.dataType() is not DataType.Data and (self.truthMetVars or autoTruthMetVars):
213  ntupleMaker = self.createOutputAlgs(config, f'TruthMetNTupleMaker{postfix}', self.truthMetVars | autoTruthMetVars, isMet=True)
214  ntupleMaker.termName = self.truthMetTermName
215 
216  treeFiller = config.createAlgorithm( 'CP::TreeFillerAlg', 'TreeFiller' + postfix )
217  treeFiller.TreeName = self.treeName
218  treeFiller.RootStreamName = self.streamName
219 
220 
221 

◆ makeSelectionSummaryAlg()

def python.OutputAnalysisConfig.OutputAnalysisConfig.makeSelectionSummaryAlg (   self,
  config,
  containerName,
  selectionName 
)
Schedule an algorithm to pick up all cut flags for a given selectionName.
The summary selection flag is written to output as selectionFlagPrefix_selectionName.

Definition at line 249 of file OutputAnalysisConfig.py.

249  def makeSelectionSummaryAlg(self, config, containerName, selectionName):
250  """
251  Schedule an algorithm to pick up all cut flags for a given selectionName.
252  The summary selection flag is written to output as selectionFlagPrefix_selectionName.
253  """
254  alg = config.createAlgorithm( 'CP::AsgSelectionAlg',
255  f'ObjectSelectionSummary_{containerName}_{selectionName}')
256  selectionDecoration = f'baselineSelection_{selectionName}_%SYS%'
257  alg.selectionDecoration = f'{selectionDecoration},as_char'
258  alg.particles = config.readName (containerName)
259  alg.preselection = config.getFullSelection (containerName, selectionName)
260  config.addOutputVar (containerName, selectionDecoration, self.selectionFlagPrefix + '_' + selectionName)

Member Data Documentation

◆ metVars

python.OutputAnalysisConfig.OutputAnalysisConfig.metVars

Definition at line 95 of file OutputAnalysisConfig.py.

◆ truthMetVars

python.OutputAnalysisConfig.OutputAnalysisConfig.truthMetVars

Definition at line 96 of file OutputAnalysisConfig.py.

◆ vars

python.OutputAnalysisConfig.OutputAnalysisConfig.vars

Definition at line 93 of file OutputAnalysisConfig.py.

◆ varsOnlyForMC

python.OutputAnalysisConfig.OutputAnalysisConfig.varsOnlyForMC

Definition at line 94 of file OutputAnalysisConfig.py.


The documentation for this class was generated from the following file:
python.ConfigSequence.filter_dsids
def filter_dsids(filterList, config)
Definition: ConfigSequence.py:28
intersection
std::vector< std::string > intersection(std::vector< std::string > &v1, std::vector< std::string > &v2)
Definition: compareFlatTrees.cxx:25
PyAthena::repr
std::string repr(PyObject *o)
returns the string representation of a python object equivalent of calling repr(o) in python
Definition: PyAthenaUtils.cxx:106
histSizes.list
def list(name, path='/')
Definition: histSizes.py:38
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
TrigJetMonitorAlgorithm.items
items
Definition: TrigJetMonitorAlgorithm.py:71
python.processes.powheg.ZZ.ZZ.__init__
def __init__(self, base_directory, **kwargs)
Constructor: all process options are set here.
Definition: ZZ.py:18
VKalVrtAthena::varHolder_detail::clear
void clear(T &var)
Definition: NtupleVars.h:48
python.Bindings.keys
keys
Definition: Control/AthenaPython/python/Bindings.py:798