ATLAS Offline Software
Loading...
Searching...
No Matches
python.ElectronAnalysisConfig.ElectronWorkingPointConfig Class Reference
Inheritance diagram for python.ElectronAnalysisConfig.ElectronWorkingPointConfig:
Collaboration diagram for python.ElectronAnalysisConfig.ElectronWorkingPointConfig:

Public Member Functions

 __init__ (self)
 instanceName (self)
 makeAlgs (self, config)

Public Attributes

 forceFullSimConfig
 trackSelection
 containerName
 selectionName
str identificationWP
 recomputeID
 chargeIDSelectionRun2
str convSelection = "Veto":
 doFSRSelection
 closeByCorrection
 recomputeChargeID
 noEffSF
 saveDetailedSF
 saveCombinedSF

Detailed Description

the ConfigBlock for the electron working point

This may at some point be split into multiple blocks (29 Aug 22).

Definition at line 283 of file ElectronAnalysisConfig.py.

Constructor & Destructor Documentation

◆ __init__()

python.ElectronAnalysisConfig.ElectronWorkingPointConfig.__init__ ( self)

Definition at line 288 of file ElectronAnalysisConfig.py.

288 def __init__ (self) :
289 super (ElectronWorkingPointConfig, self).__init__ ()
290 self.addOption ('containerName', '', type=str,
291 noneAction='error',
292 info="the name of the input container.")
293 self.addOption ('selectionName', '', type=str,
294 noneAction='error',
295 info="the name of the electron selection to define (e.g. tight or "
296 "loose).")
297 self.addOption ('postfix', None, type=str,
298 info="a postfix to apply to decorations and algorithm names. "
299 "Typically not needed here as selectionName is used internally.")
300 self.addOption ('trackSelection', True, type=bool,
301 info="whether or not to set up an instance of "
302 "CP::AsgLeptonTrackSelectionAlg, with the recommended d_0 and "
303 "z_0 sin(theta) cuts. The default is True.")
304 self.addOption ('maxD0Significance', 5, type=float,
305 info="maximum d0 significance used for the trackSelection"
306 "The default is 5")
307 self.addOption ('maxDeltaZ0SinTheta', 0.5, type=float,
308 info="maximum z0sinTheta in mm used for the trackSelection"
309 "The default is 0.5 mm")
310 self.addOption ('identificationWP', None, type=str,
311 info="the ID WP (string) to use. Supported ID WPs: TightLH, "
312 "MediumLH, LooseBLayerLH, TightDNN, MediumDNN, LooseDNN, "
313 "TightNoCFDNN, MediumNoCFDNN, VeryLooseNoCF97DNN, NoID.",
314 expertMode=["NoID"])
315 self.addOption ('isolationWP', None, type=str,
316 info="the isolation WP (string) to use. Supported isolation WPs: "
317 "HighPtCaloOnly, Loose_VarRad, Tight_VarRad, TightTrackOnly_"
318 "VarRad, TightTrackOnly_FixedRad, NonIso.")
319 self.addOption ('convSelection', None, type=str,
320 info="enter additional selection (string) to use. To be used with "
321 "TightLH or will crash. Supported keywords:"
322 "Veto, MatConv, GammaStar.")
323 self.addOption ('addSelectionToPreselection', True, type=bool,
324 info="whether to retain only electrons satisfying the working point "
325 "requirements. The default is True.")
326 self.addOption ('closeByCorrection', False, type=bool,
327 info="whether to use close-by-corrected isolation working points")
328 self.addOption ('recomputeID', False, type=bool,
329 info="whether to rerun the ID LH/DNN. The default is False, i.e. to use "
330 "derivation flags.")
331 self.addOption ('chargeIDSelectionRun2', False, type=bool,
332 info="whether to run the ECIDS tool. Only available for run 2. "
333 "The default is False.")
334 self.addOption ('recomputeChargeID', False, type=bool,
335 info="whether to rerun the ECIDS. The default is False, i.e. to use "
336 "derivation flags.")
337 self.addOption ('doFSRSelection', False, type=bool,
338 info="whether to accept additional electrons close to muons for "
339 "the purpose of FSR corrections to these muons. Expert feature "
340 "requested by the H4l analysis running on PHYSLITE. "
341 "The default is False.",
342 expertMode=True)
343 self.addOption ('noEffSF', False, type=bool,
344 info="disables the calculation of efficiencies and scale factors. "
345 "Experimental! only useful to test a new WP for which scale "
346 "factors are not available. The default is False.",
347 expertMode=True)
348 self.addOption ('saveDetailedSF', True, type=bool,
349 info="save all the independent detailed object scale factors. "
350 "The default is True.")
351 self.addOption ('saveCombinedSF', False, type=bool,
352 info="save the combined object scale factor. "
353 "The default is False.")
354 self.addOption ('forceFullSimConfig', False, type=bool,
355 info="whether to force the tool to use the configuration meant for "
356 "full simulation samples. Only for testing purposes. "
357 "The default is False.")
358 self.addOption ('correlationModelId', 'SIMPLIFIED', type=str,
359 info="the correlation model (string) to use for ID scale factors "
360 "Supported models: SIMPLIFIED (default), FULL, TOTAL, TOYS")
361 self.addOption ('correlationModelIso', 'SIMPLIFIED', type=str,
362 info="the correlation model (string) to use for isolation scale factors "
363 "Supported models: SIMPLIFIED (default), FULL, TOTAL, TOYS")
364 self.addOption ('correlationModelReco', 'SIMPLIFIED', type=str,
365 info="the correlation model (string) to use for reconstruction scale factors "
366 "Supported models: SIMPLIFIED (default), FULL, TOTAL, TOYS")
367 self.addOption('addChargeMisIDSF', False, type=bool,
368 info="Adds scale factors for charge-misID.")
369

Member Function Documentation

◆ instanceName()

python.ElectronAnalysisConfig.ElectronWorkingPointConfig.instanceName ( self)
Return the instance name for this block

Definition at line 370 of file ElectronAnalysisConfig.py.

370 def instanceName (self) :
371 """Return the instance name for this block"""
372 if self.postfix is not None :
373 return self.containerName + '_' + self.selectionName + self.postfix
374 return self.containerName + '_' + self.selectionName
375

◆ makeAlgs()

python.ElectronAnalysisConfig.ElectronWorkingPointConfig.makeAlgs ( self,
config )

Definition at line 376 of file ElectronAnalysisConfig.py.

376 def makeAlgs (self, config) :
377
378 log = logging.getLogger('ElectronWorkingPointConfig')
379
380 if self.forceFullSimConfig:
381 log.warning("You are running ElectronWorkingPointConfig forcing full sim config")
382 log.warning("This is only intended to be used for testing purposes")
383
384 selectionPostfix = self.selectionName
385 if selectionPostfix != '' and selectionPostfix[0] != '_' :
386 selectionPostfix = '_' + selectionPostfix
387
388 # The setup below is inappropriate for Run 1
389 if config.geometry() is LHCPeriod.Run1:
390 raise ValueError ("Can't set up the ElectronWorkingPointConfig with %s, there must be something wrong!" % config.geometry().value)
391
392 postfix = self.postfix
393 if postfix is None :
394 postfix = self.selectionName
395 if postfix != '' and postfix[0] != '_' :
396 postfix = '_' + postfix
397
398 # Set up the track selection algorithm:
399 if self.trackSelection :
400 alg = config.createAlgorithm( 'CP::AsgLeptonTrackSelectionAlg',
401 'ElectronTrackSelectionAlg',
402 reentrant=True )
403 alg.selectionDecoration = 'trackSelection' + postfix + ',as_bits'
404 alg.maxD0Significance = self.maxD0Significance
405 alg.maxDeltaZ0SinTheta = self.maxDeltaZ0SinTheta
406 alg.particles = config.readName (self.containerName)
407 alg.preselection = config.getPreselection (self.containerName, '')
408 if self.trackSelection :
409 config.addSelection (self.containerName, self.selectionName, alg.selectionDecoration,
410 preselection=self.addSelectionToPreselection)
411
412 if 'LH' in self.identificationWP:
413 # Set up the likelihood ID selection algorithm
414 # It is safe to do this before calibration, as the cluster E is used
415 alg = config.createAlgorithm( 'CP::AsgSelectionAlg', 'ElectronLikelihoodAlg' )
416 alg.selectionDecoration = 'selectLikelihood' + selectionPostfix + ',as_char'
417 if self.recomputeID:
418 # Rerun the likelihood ID
419 config.addPrivateTool( 'selectionTool', 'AsgElectronLikelihoodTool' )
420 alg.selectionTool.primaryVertexContainer = 'PrimaryVertices'
421 # Here we have to match the naming convention of EGSelectorConfigurationMapping.h
422 # which differ from the one used for scale factors
423 if config.geometry() >= LHCPeriod.Run3:
424 if 'HI' not in self.identificationWP:
425 alg.selectionTool.WorkingPoint = self.identificationWP.replace("BLayer","BL") + 'Electron'
426 else:
427 alg.selectionTool.WorkingPoint = self.identificationWP.replace('_HI', 'Electron_HI')
428 elif config.geometry() is LHCPeriod.Run2:
429 alg.selectionTool.WorkingPoint = self.identificationWP.replace("BLayer","BL") + 'Electron_Run2'
430 else:
431 # Select from Derivation Framework flags
432 config.addPrivateTool( 'selectionTool', 'CP::AsgFlagSelectionTool' )
433 dfFlag = "DFCommonElectronsLH" + self.identificationWP.split('LH')[0]
434 dfFlag = dfFlag.replace("BLayer","BL")
435 alg.selectionTool.selectionFlags = [dfFlag]
436 elif 'SiHit' in self.identificationWP:
437 # Only want SiHit electrons, so veto loose LH electrons
438 algVeto = config.createAlgorithm( 'CP::AsgSelectionAlg', 'ElectronLikelihoodAlgVeto')
439 algVeto.selectionDecoration = 'selectLikelihoodVeto' + postfix + ',as_char'
440 config.addPrivateTool( 'selectionTool', 'CP::AsgFlagSelectionTool' )
441 algVeto.selectionTool.selectionFlags = ["DFCommonElectronsLHLoose"]
442 algVeto.selectionTool.invertFlags = [True]
443 algVeto.particles = config.readName (self.containerName)
444 algVeto.preselection = config.getPreselection (self.containerName, self.selectionName)
445 # add the veto as a selection
446 config.addSelection (self.containerName, self.selectionName, algVeto.selectionDecoration,
447 preselection=self.addSelectionToPreselection)
448
449 # Select SiHit electrons using IsEM bits
450 alg = config.createAlgorithm( 'CP::AsgSelectionAlg', 'ElectronLikelihoodAlg' )
451 alg.selectionDecoration = 'selectSiHit' + selectionPostfix + ',as_char'
452 # Select from Derivation Framework IsEM bits
453 config.addPrivateTool( 'selectionTool', 'CP::AsgMaskSelectionTool' )
454 dfVar = "DFCommonElectronsLHLooseBLIsEMValue"
455 alg.selectionTool.selectionVars = [dfVar]
456 mask = int( 0 | 0x1 << 1 | 0x1 << 2)
457 alg.selectionTool.selectionMasks = [mask]
458 elif 'DNN' in self.identificationWP:
459 if self.chargeIDSelectionRun2:
460 raise ValueError('DNN is not intended to be used with '
461 '`chargeIDSelectionRun2` option as there are '
462 'DNN WPs containing charge flip rejection.')
463 # Set up the DNN ID selection algorithm
464 alg = config.createAlgorithm( 'CP::AsgSelectionAlg', 'ElectronDNNAlg' )
465 alg.selectionDecoration = 'selectDNN' + selectionPostfix + ',as_char'
466 if self.recomputeID:
467 # Rerun the DNN ID
468 config.addPrivateTool( 'selectionTool', 'AsgElectronSelectorTool' )
469 # Here we have to match the naming convention of EGSelectorConfigurationMapping.h
470 if config.geometry() is LHCPeriod.Run3:
471 raise ValueError ( "DNN working points are not available for Run 3 yet.")
472 else:
473 alg.selectionTool.WorkingPoint = self.identificationWP + 'Electron'
474 else:
475 # Select from Derivation Framework flags
476 config.addPrivateTool( 'selectionTool', 'CP::AsgFlagSelectionTool' )
477 dfFlag = "DFCommonElectronsDNN" + self.identificationWP.split('DNN')[0]
478 alg.selectionTool.selectionFlags = [dfFlag]
479 elif self.identificationWP == 'NoID':
480 alg = None
481 else:
482 raise ValueError (f"Electron ID working point '{self.identificationWP}' is not recognised!")
483
484 if alg is not None:
485 alg.particles = config.readName (self.containerName)
486 alg.preselection = config.getPreselection (self.containerName, self.selectionName)
487 config.addSelection (self.containerName, self.selectionName, alg.selectionDecoration,
488 preselection=self.addSelectionToPreselection)
489
490 # maintain order of selections
491 if 'SiHit' in self.identificationWP:
492 # Set up the ElectronSiHitDecAlg algorithm to decorate SiHit electrons with a minimal amount of information:
493 algDec = config.createAlgorithm( 'CP::ElectronSiHitDecAlg', 'ElectronSiHitDecAlg' )
494 selDec = 'siHitEvtHasLeptonPair' + selectionPostfix + ',as_char'
495 algDec.selectionName = selDec.split(",")[0]
496 algDec.ElectronContainer = config.readName (self.containerName)
497 # Set flag to only collect SiHit electrons for events with an electron or muon pair to minimize size increase from SiHit electrons
498 algDec.RequireTwoLeptons = True
499 config.addSelection (self.containerName, self.selectionName, selDec,
500 preselection=self.addSelectionToPreselection)
501
502 # Additional selection for conversions and gamma*
503 if self.convSelection is not None:
504 # skip if not applied together with TightLH
505 if self.identificationWP != 'TightLH':
506 raise ValueError(f"convSelection can only be used with TightLH ID, "
507 f"whereas {self.identificationWP} has been selected. convSelection option will be ignored.")
508 # check if allowed value
509 allowedValues = ["Veto", "GammaStar", "MatConv"]
510 if self.convSelection not in allowedValues:
511 raise ValueError(f"convSelection has been set to {self.convSelection}, which is not a valid option. "
512 f"convSelection option must be one of {allowedValues}.")
513
514 # ambiguityType == 0
515 alg = config.createAlgorithm( 'CP::AsgSelectionAlg', 'ElectronAmbiguityTypeAlg' )
516 alg.selectionDecoration = 'selectAmbiguityType' + selectionPostfix + ',as_char'
517 config.addPrivateTool( 'selectionTool', 'CP::AsgNumDecorationSelectionToolUInt8' )
518 alg.selectionTool.decorationName = "ambiguityType"
519 alg.selectionTool.doEqual = True
520 alg.selectionTool.equal = 0
521 alg.particles = config.readName (self.containerName)
522 alg.preselection = config.getPreselection (self.containerName, self.selectionName)
523 config.addSelection (self.containerName, self.selectionName, alg.selectionDecoration,
524 preselection=self.addSelectionToPreselection)
525
526 # DFCommonAddAmbiguity selection
527 alg = config.createAlgorithm( 'CP::AsgSelectionAlg', 'ElectronDFCommonAddAmbiguityAlg' )
528 alg.selectionDecoration = 'selectDFCommonAddAmbiguity' + selectionPostfix + ',as_char'
529 config.addPrivateTool( 'selectionTool', 'CP::AsgNumDecorationSelectionToolInt' )
530 alg.selectionTool.decorationName = "DFCommonAddAmbiguity"
531 if self.convSelection == "Veto":
532 alg.selectionTool.doMax = True
533 alg.selectionTool.max = 1
534 elif self.convSelection == "GammaStar":
535 alg.selectionTool.doEqual = True
536 alg.selectionTool.equal = 1
537 elif self.convSelection == "MatConv":
538 alg.selectionTool.doEqual = True
539 alg.selectionTool.equal = 2
540 alg.particles = config.readName (self.containerName)
541 alg.preselection = config.getPreselection (self.containerName, self.selectionName)
542 config.addSelection (self.containerName, self.selectionName, alg.selectionDecoration,
543 preselection=self.addSelectionToPreselection)
544
545 # Set up the FSR selection
546 if self.doFSRSelection :
547 # save the flag set for the WP
548 wpFlag = alg.selectionDecoration.split(",")[0]
549 alg = config.createAlgorithm( 'CP::EgammaFSRForMuonsCollectorAlg', 'EgammaFSRForMuonsCollectorAlg' )
550 alg.selectionDecoration = wpFlag
551 alg.ElectronOrPhotonContKey = config.readName (self.containerName)
552 # For SiHit electrons, set flag to remove FSR electrons.
553 # For standard electrons, FSR electrons need to be added as they may be missed by the standard selection.
554 # For SiHit electrons FSR electrons are generally always selected, so they should be removed since they will be in the standard electron container.
555 if 'SiHit' in self.identificationWP:
556 alg.vetoFSR = True
557
558 # Set up the isolation selection algorithm:
559 if self.isolationWP != 'NonIso' :
560 alg = config.createAlgorithm( 'CP::EgammaIsolationSelectionAlg',
561 'ElectronIsolationSelectionAlg' )
562 alg.selectionDecoration = 'isolated' + selectionPostfix + ',as_char'
563 config.addPrivateTool( 'selectionTool', 'CP::IsolationSelectionTool' )
564 alg.selectionTool.ElectronWP = self.isolationWP
565 if self.closeByCorrection:
566 alg.selectionTool.IsoDecSuffix = "CloseByCorr"
567 alg.egammas = config.readName (self.containerName)
568 alg.preselection = config.getPreselection (self.containerName, self.selectionName)
569 config.addSelection (self.containerName, self.selectionName, alg.selectionDecoration,
570 preselection=self.addSelectionToPreselection)
571
572 if self.chargeIDSelectionRun2 and config.geometry() >= LHCPeriod.Run3:
573 log.warning("ECIDS is only available for Run 2 and will not have any effect in Run 3.")
574
575 # Select electrons only if they don't appear to have flipped their charge.
576 if self.chargeIDSelectionRun2 and config.geometry() < LHCPeriod.Run3:
577 alg = config.createAlgorithm( 'CP::AsgSelectionAlg',
578 'ElectronChargeIDSelectionAlg' )
579 alg.selectionDecoration = 'chargeID' + selectionPostfix + ',as_char'
580 if self.recomputeChargeID:
581 # Rerun the ECIDS BDT
582 config.addPrivateTool( 'selectionTool',
583 'AsgElectronChargeIDSelectorTool' )
584 alg.selectionTool.TrainingFile = \
585 'ElectronPhotonSelectorTools/ChargeID/ECIDS_20180731rel21Summer2018.root'
586 alg.selectionTool.WorkingPoint = 'Loose'
587 alg.selectionTool.CutOnBDT = -0.337671 # Loose 97%
588 else:
589 # Select from Derivation Framework flags
590 config.addPrivateTool( 'selectionTool', 'CP::AsgFlagSelectionTool' )
591 alg.selectionTool.selectionFlags = ["DFCommonElectronsECIDS"]
592
593 alg.particles = config.readName (self.containerName)
594 alg.preselection = config.getPreselection (self.containerName, self.selectionName)
595 config.addSelection (self.containerName, self.selectionName, alg.selectionDecoration,
596 preselection=self.addSelectionToPreselection)
597
598 correlationModels = ["SIMPLIFIED", "FULL", "TOTAL", "TOYS"]
599 map_file = 'ElectronEfficiencyCorrection/2015_2025/rel22.2/2025_Run2Rel22_Recommendation_v3/map1.txt' \
600 if config.geometry() is LHCPeriod.Run2 else \
601 'ElectronEfficiencyCorrection/2015_2025/rel22.2/2025_Run3_Consolidated_Recommendation_v4/map2.txt'
602 sfList = []
603 # Set up the RECO electron efficiency correction algorithm:
604 if config.dataType() is not DataType.Data and not self.noEffSF:
605 if 'DNN' in self.identificationWP:
606 raise ValueError('DNN does not yet have efficiency correction, '
607 'please disable it by setting `noEffSF` to True.')
608
609 alg = config.createAlgorithm( 'CP::ElectronEfficiencyCorrectionAlg',
610 'ElectronEfficiencyCorrectionAlgReco' )
611 config.addPrivateTool( 'efficiencyCorrectionTool',
612 'AsgElectronEfficiencyCorrectionTool' )
613 alg.scaleFactorDecoration = 'el_reco_effSF' + selectionPostfix + '_%SYS%'
614 alg.efficiencyCorrectionTool.MapFilePath = map_file
615 alg.efficiencyCorrectionTool.RecoKey = "Reconstruction"
616 if self.correlationModelReco not in correlationModels:
617 raise ValueError('Invalid correlation model for reconstruction efficiency, '
618 f'has to be one of: {", ".join(correlationModels)}')
619 if config.geometry() >= LHCPeriod.Run3 and self.correlationModelReco != "TOTAL":
620 log.warning("Only TOTAL correlation model is currently supported "
621 "for reconstruction efficiency correction in Run 3.")
622 alg.efficiencyCorrectionTool.CorrelationModel = "TOTAL"
623 else:
624 alg.efficiencyCorrectionTool.CorrelationModel = self.correlationModelReco
625 if config.dataType() is DataType.FastSim:
626 alg.efficiencyCorrectionTool.ForceDataType = (
627 PATCore.ParticleDataType.Full if self.forceFullSimConfig
628 else PATCore.ParticleDataType.Fast)
629 elif config.dataType() is DataType.FullSim:
630 alg.efficiencyCorrectionTool.ForceDataType = \
631 PATCore.ParticleDataType.Full
632 alg.outOfValidity = 2 #silent
633 alg.outOfValidityDeco = 'el_reco_bad_eff' + selectionPostfix
634 alg.electrons = config.readName (self.containerName)
635 alg.preselection = config.getPreselection (self.containerName, self.selectionName)
636 if self.saveDetailedSF:
637 config.addOutputVar (self.containerName, alg.scaleFactorDecoration,
638 'reco_effSF' + postfix)
639 sfList += [alg.scaleFactorDecoration]
640
641 # Set up the ID electron efficiency correction algorithm:
642 if config.dataType() is not DataType.Data and not self.noEffSF and self.identificationWP != 'NoID':
643
644 alg = config.createAlgorithm( 'CP::ElectronEfficiencyCorrectionAlg',
645 'ElectronEfficiencyCorrectionAlgID' )
646 config.addPrivateTool( 'efficiencyCorrectionTool',
647 'AsgElectronEfficiencyCorrectionTool' )
648 alg.scaleFactorDecoration = 'el_id_effSF' + selectionPostfix + '_%SYS%'
649 alg.efficiencyCorrectionTool.MapFilePath = map_file
650 alg.efficiencyCorrectionTool.IdKey = self.identificationWP.replace("LH","")
651 if self.correlationModelId not in correlationModels:
652 raise ValueError('Invalid correlation model for identification efficiency, '
653 f'has to be one of: {", ".join(correlationModels)}')
654 alg.efficiencyCorrectionTool.CorrelationModel = self.correlationModelId
655 if config.dataType() is DataType.FastSim:
656 alg.efficiencyCorrectionTool.ForceDataType = (
657 PATCore.ParticleDataType.Full if self.forceFullSimConfig
658 else PATCore.ParticleDataType.Fast)
659 elif config.dataType() is DataType.FullSim:
660 alg.efficiencyCorrectionTool.ForceDataType = \
661 PATCore.ParticleDataType.Full
662 alg.outOfValidity = 2 #silent
663 alg.outOfValidityDeco = 'el_id_bad_eff' + selectionPostfix
664 alg.electrons = config.readName (self.containerName)
665 alg.preselection = config.getPreselection (self.containerName, self.selectionName)
666 if self.saveDetailedSF:
667 config.addOutputVar (self.containerName, alg.scaleFactorDecoration,
668 'id_effSF' + postfix)
669 sfList += [alg.scaleFactorDecoration]
670
671 # Set up the ISO electron efficiency correction algorithm:
672 if config.dataType() is not DataType.Data and self.isolationWP != 'NonIso' and not self.noEffSF:
673 alg = config.createAlgorithm( 'CP::ElectronEfficiencyCorrectionAlg',
674 'ElectronEfficiencyCorrectionAlgIsol' )
675 config.addPrivateTool( 'efficiencyCorrectionTool',
676 'AsgElectronEfficiencyCorrectionTool' )
677 alg.scaleFactorDecoration = 'el_isol_effSF' + selectionPostfix + '_%SYS%'
678 alg.efficiencyCorrectionTool.MapFilePath = map_file
679 alg.efficiencyCorrectionTool.IdKey = self.identificationWP.replace("LH","")
680 alg.efficiencyCorrectionTool.IsoKey = self.isolationWP
681 if self.correlationModelIso not in correlationModels:
682 raise ValueError('Invalid correlation model for isolation efficiency, '
683 f'has to be one of: {", ".join(correlationModels)}')
684 if self.correlationModelIso != 'TOTAL':
685 log.warning("Only TOTAL correlation model is currently supported "
686 "for isolation efficiency correction in Run 3.")
687 alg.efficiencyCorrectionTool.CorrelationModel = "TOTAL"
688 if config.dataType() is DataType.FastSim:
689 alg.efficiencyCorrectionTool.ForceDataType = (
690 PATCore.ParticleDataType.Full if self.forceFullSimConfig
691 else PATCore.ParticleDataType.Fast)
692 elif config.dataType() is DataType.FullSim:
693 alg.efficiencyCorrectionTool.ForceDataType = \
694 PATCore.ParticleDataType.Full
695 alg.outOfValidity = 2 #silent
696 alg.outOfValidityDeco = 'el_isol_bad_eff' + selectionPostfix
697 alg.electrons = config.readName (self.containerName)
698 alg.preselection = config.getPreselection (self.containerName, self.selectionName)
699 if self.saveDetailedSF:
700 config.addOutputVar (self.containerName, alg.scaleFactorDecoration,
701 'isol_effSF' + postfix)
702 sfList += [alg.scaleFactorDecoration]
703
704 if (self.chargeIDSelectionRun2 and config.geometry() < LHCPeriod.Run3 and
705 config.dataType() is not DataType.Data and not self.noEffSF):
706 alg = config.createAlgorithm( 'CP::ElectronEfficiencyCorrectionAlg',
707 'ElectronEfficiencyCorrectionAlgEcids' )
708 config.addPrivateTool( 'efficiencyCorrectionTool',
709 'AsgElectronEfficiencyCorrectionTool' )
710 alg.scaleFactorDecoration = 'el_ecids_effSF' + selectionPostfix + '_%SYS%'
711 if self.isolationWP != 'Tight_VarRad':
712 raise ValueError('ECIDS SFs are supported only for Tight_VarRad isolation.')
713 if self.identificationWP == 'LooseBLayerLH':
714 ecids_lh = 'loose'
715 elif self.identificationWP == 'MediumLH':
716 ecids_lh = 'medium'
717 elif self.identificationWP == 'TightLH':
718 ecids_lh = 'tight'
719 else:
720 raise ValueError('ECIDS SFs are supported only for ID LooseBLayerLH, MediumLH, or TightLH')
721
722 alg.efficiencyCorrectionTool.CorrelationModel = "TOTAL"
723 alg.efficiencyCorrectionTool.CorrectionFileNameList = \
724 [f'ElectronEfficiencyCorrection/2015_2025/rel22.2/2025_Run2Rel22_Recommendation_v2/ecids/efficiencySF.ChargeID.{ecids_lh}_ECIDS_Tight_VarRad.root']
725 if config.dataType() is DataType.FastSim:
726 alg.efficiencyCorrectionTool.ForceDataType = (
727 PATCore.ParticleDataType.Full if self.forceFullSimConfig
728 else PATCore.ParticleDataType.Fast)
729 elif config.dataType() is DataType.FullSim:
730 alg.efficiencyCorrectionTool.ForceDataType = \
731 PATCore.ParticleDataType.Full
732 alg.outOfValidity = 2 #silent
733 alg.outOfValidityDeco = 'el_ecids_bad_eff' + selectionPostfix
734 alg.electrons = config.readName (self.containerName)
735 alg.preselection = config.getPreselection (self.containerName, self.selectionName)
736 if self.saveDetailedSF:
737 config.addOutputVar (self.containerName, alg.scaleFactorDecoration,
738 'ecids_effSF' + postfix)
739 sfList += [alg.scaleFactorDecoration]
740
741 if self.addChargeMisIDSF and config.dataType() is not DataType.Data and not self.noEffSF:
742 if config.geometry() >= LHCPeriod.Run3:
743 raise ValueError('Run 3 does not yet have charge mis-ID correction, '
744 'please disable it by setting `noEffSF` to False.')
745
746 alg = config.createAlgorithm( 'CP::ElectronEfficiencyCorrectionAlg',
747 'ElectronEfficiencyCorrectionAlgMisid' )
748 config.addPrivateTool( 'efficiencyCorrectionTool',
749 'CP::ElectronChargeEfficiencyCorrectionTool' )
750 alg.scaleFactorDecoration = 'el_charge_misid_effSF' + selectionPostfix + '_%SYS%'
751 if self.isolationWP != 'Tight_VarRad':
752 raise ValueError('Charge mis-ID SFs are supported only for Tight_VarRad isolation.')
753 if self.identificationWP == 'LooseBLayerLH':
754 misid_lh = 'LooseAndBLayerLLH'
755 elif self.identificationWP == 'MediumLH':
756 misid_lh = 'MediumLLH'
757 elif self.identificationWP == 'TightLH':
758 misid_lh = 'TightLLH'
759 else:
760 raise ValueError('Charge mis-ID SFs are supported only for ID LooseBLayerLH, MediumLH, or TightLH')
761 misid_suffix = '_ECIDSloose' if self.chargeIDSelectionRun2 else ''
762
763 alg.efficiencyCorrectionTool.CorrectionFileName = \
764 f'ElectronEfficiencyCorrection/2015_2025/rel22.2/2025_Run2Rel22_Recommendation_v2/charge_misID/chargeEfficiencySF.{misid_lh}_d0z0_TightVarRad{misid_suffix}.root'
765 if config.dataType() is DataType.FastSim:
766 alg.efficiencyCorrectionTool.ForceDataType = (
767 PATCore.ParticleDataType.Full if self.forceFullSimConfig
768 else PATCore.ParticleDataType.Fast)
769 elif config.dataType() is DataType.FullSim:
770 alg.efficiencyCorrectionTool.ForceDataType = \
771 PATCore.ParticleDataType.Full
772 alg.outOfValidity = 2 #silent
773 alg.outOfValidityDeco = 'el_misid_bad_eff' + selectionPostfix
774 alg.electrons = config.readName (self.containerName)
775 alg.preselection = config.getPreselection (self.containerName, self.selectionName)
776 if self.saveDetailedSF:
777 config.addOutputVar (self.containerName, alg.scaleFactorDecoration,
778 'charge_misid_effSF' + postfix)
779 sfList += [alg.scaleFactorDecoration]
780
781 if config.dataType() is not DataType.Data and not self.noEffSF and self.saveCombinedSF:
782 alg = config.createAlgorithm( 'CP::AsgObjectScaleFactorAlg',
783 'ElectronCombinedEfficiencyScaleFactorAlg' )
784 alg.particles = config.readName (self.containerName)
785 alg.inScaleFactors = sfList
786 alg.outScaleFactor = 'effSF' + postfix + '_%SYS%'
787 config.addOutputVar (self.containerName, alg.outScaleFactor, 'effSF' + postfix)
788
789
790
std::string replace(std::string s, const std::string &s2, const std::string &s3)
Definition hcg.cxx:310
std::vector< std::string > split(const std::string &s, const std::string &t=":")
Definition hcg.cxx:177

Member Data Documentation

◆ chargeIDSelectionRun2

python.ElectronAnalysisConfig.ElectronWorkingPointConfig.chargeIDSelectionRun2

Definition at line 459 of file ElectronAnalysisConfig.py.

◆ closeByCorrection

python.ElectronAnalysisConfig.ElectronWorkingPointConfig.closeByCorrection

Definition at line 565 of file ElectronAnalysisConfig.py.

◆ containerName

python.ElectronAnalysisConfig.ElectronWorkingPointConfig.containerName

Definition at line 409 of file ElectronAnalysisConfig.py.

◆ convSelection

str python.ElectronAnalysisConfig.ElectronWorkingPointConfig.convSelection = "Veto":

Definition at line 531 of file ElectronAnalysisConfig.py.

◆ doFSRSelection

python.ElectronAnalysisConfig.ElectronWorkingPointConfig.doFSRSelection

Definition at line 546 of file ElectronAnalysisConfig.py.

◆ forceFullSimConfig

python.ElectronAnalysisConfig.ElectronWorkingPointConfig.forceFullSimConfig

Definition at line 380 of file ElectronAnalysisConfig.py.

◆ identificationWP

str python.ElectronAnalysisConfig.ElectronWorkingPointConfig.identificationWP

Definition at line 412 of file ElectronAnalysisConfig.py.

◆ noEffSF

python.ElectronAnalysisConfig.ElectronWorkingPointConfig.noEffSF

Definition at line 604 of file ElectronAnalysisConfig.py.

◆ recomputeChargeID

python.ElectronAnalysisConfig.ElectronWorkingPointConfig.recomputeChargeID

Definition at line 580 of file ElectronAnalysisConfig.py.

◆ recomputeID

python.ElectronAnalysisConfig.ElectronWorkingPointConfig.recomputeID

Definition at line 417 of file ElectronAnalysisConfig.py.

◆ saveCombinedSF

python.ElectronAnalysisConfig.ElectronWorkingPointConfig.saveCombinedSF

Definition at line 781 of file ElectronAnalysisConfig.py.

◆ saveDetailedSF

python.ElectronAnalysisConfig.ElectronWorkingPointConfig.saveDetailedSF

Definition at line 636 of file ElectronAnalysisConfig.py.

◆ selectionName

python.ElectronAnalysisConfig.ElectronWorkingPointConfig.selectionName

Definition at line 409 of file ElectronAnalysisConfig.py.

◆ trackSelection

python.ElectronAnalysisConfig.ElectronWorkingPointConfig.trackSelection

Definition at line 399 of file ElectronAnalysisConfig.py.


The documentation for this class was generated from the following file: