def PlotSignal(datasetsMgr, dataPath, opts): Verbose("Plotting Ctrl Plots with Signal") # Definitions histoList = datasetsMgr.getDataset("Data").getDirectoryContent(dataPath) histoPaths = [dataPath + "/" + h for h in histoList] histoKwargs = GetHistoKwargs(histoPaths, opts) saveFormats = [".C", ".png", ".pdf"] # Create/Draw the plots for histoName in histoPaths: if "_afterstandardselections" not in histoName.lower(): continue # Skip TH2 plots if "JetEtaPhi_" in histoName: continue kwargs_ = histoKwargs[histoName] saveName = histoName.replace("/", "") # Create the plot p = plots.DataMCPlot(datasetsMgr, histoName, saveFormats=[]) # Customise style p.histoMgr.forHisto("ChargedHiggs_HplusTB_HplusToTB_M_500", styles.getSignalStyleHToTB()) # Draw the plot plots.drawPlot(p, saveName, **kwargs_) #the "**" unpacks the kwargs_ dictionary # Save plot in all formats SavePlot(p, histoName, os.path.join(opts.saveDir, "Signal", opts.optMode)) return
def getMt(datasets, bins, name, normalization): for i, bin in enumerate(bins): mtplot = plots.DataMCPlot(datasets, name + "/" + name + bin) if i == 0: mt = mtplot.histoMgr.getHisto("Data").getRootHisto().Clone(name + "/" + name + bin) mt_ewk = mtplot.histoMgr.getHisto("EWK").getRootHisto().Clone( name + "/" + name + bin) mt.Add(mt_ewk, -1) scale = normalization[i] mt.Scale(scale) if i != 0 and bin != "Inclusive": h = mtplot.histoMgr.getHisto("Data").getRootHisto().Clone(name + "/" + name + bin) mt_ewk = mtplot.histoMgr.getHisto("EWK").getRootHisto().Clone( name + "/" + name + bin) h.Add(mt_ewk, -1) scale = normalization[i] h.Scale(scale) mt.Add(h) return mt
def GetRootHistos(datasetsMgr, histoList, regions, binLabels): # Definition hPathDict = GetHistoPathDict(histoList, printList=False) rhDict = {} # For-loop: All Control Regions (CR) for region in regions: # For-loop: All bins for binLabel in binLabels: # Define labels lIncl = "%s-%s" % (region, binLabel) lGenB = "%s-%s-%s" % (region, binLabel, "EWKGenuineB") lFakeB = "%s-%s-%s" % (region, binLabel, "EWKFakeB") # Get the desired histograms pIncl = plots.DataMCPlot(datasetsMgr, hPathDict[lIncl]) pGenB = plots.DataMCPlot(datasetsMgr, hPathDict[lGenB]) pFakeB = plots.DataMCPlot(datasetsMgr, hPathDict[lFakeB]) # Clone and Save the root histograms rhDict["Data-" + lIncl] = pIncl.histoMgr.getHisto( "Data").getRootHisto().Clone("Data-" + lIncl) rhDict["EWK-" + lGenB] = pGenB.histoMgr.getHisto( "EWK").getRootHisto().Clone("EWK-" + lGenB) rhDict["EWK-" + lFakeB] = pFakeB.histoMgr.getHisto( "EWK").getRootHisto().Clone("EWK-" + lFakeB) if opts.useMC: rhDict["QCD-" + lIncl] = pIncl.histoMgr.getHisto( "QCD").getRootHisto().Clone("QCD-" + lIncl) # Add EWKFakeB (MC) to QCD (MC) to get FakeB (= QCD_inclusive + EWK_fakeB) rhDict["FakeB-" + lIncl] = rhDict["QCD- " + lIncl].Clone("FakeB-" + lIncl) rhDict["FakeB-" + lIncl].Add(rhDict["EWK-" + lFakeB], +1) else: # Subtract EWKGenuineB (MC) from Data to get FakeB (= Data - EWK_genuineB) rhDict["FakeB-" + lIncl] = rhDict["Data-" + lIncl].Clone("FakeB-" + lIncl) rhDict["FakeB-" + lIncl].Add(rhDict["EWK-" + lGenB], -1) # For debugging: if 0: for k in rhDict: if "FakeB" not in k: continue fakeBResult.PrintTH1Info(rhDict[k]) return rhDict
def PlotHistograms(datasetsMgr, histoName, signalsList, cutDir): # Get Histogram name and its kwargs saveName = histoName.rsplit("/")[-1] kwargs = GetHistoKwargs(saveName, opts) # Create the plot if "Data" in datasetsMgr.getAllDatasetNames(): p1 = plots.DataMCPlot(datasetsMgr, histoName, saveFormats=[]) else: if opts.normalizeToLumi: p1 = plots.MCPlot(datasetsMgr, histoName, normalizeToLumi=opts.intLumi, saveFormats=[]) #elif opts.normalizeByCrossSection: # p1 = plots.MCPlot(datasetsMgr, histoName, normalizeByCrossSection=True, saveFormats=[], **{}) else: raise Exception("One of the options --normalizeToOne, --normalizeByCrossSection, --normalizeToLumi must be enabled (set to \"True\").") # Create significance plots hList = [] for s in signalsList: hList.append(GetSignificanceHisto(p1, datasetsMgr, cutDir=cutDir, signalDataset=s)) #p2 = plots.ComparisonManyPlot(hList[0], hList[1:]) p2 = plots.PlotBase(hList, saveFormats=[]) p2.setLuminosity(opts.intLumi) # Drawing style # p2.histoMgr.setHistoDrawStyleAll("LP") # p2.histoMgr.setHistoLegendStyleAll("LP") p2.histoMgr.setHistoDrawStyleAll("HIST") p2.histoMgr.setHistoLegendStyleAll("L") p2.histoMgr.forEachHisto(lambda h: h.getRootHisto().SetMarkerSize(1.0)) p2.histoMgr.forEachHisto(lambda h: h.getRootHisto().SetLineStyle(ROOT.kSolid)) p2.histoMgr.forEachHisto(lambda h: h.getRootHisto().SetMarkerStyle(ROOT.kFullCircle)) # Draw the plot style.setLogX(opts.logX) style.setLogY(opts.logY) plots.drawPlot(p1, saveName, **kwargs) # SavePlot(p1, saveName, os.path.join(opts.saveDir), [".png", ".pdf"] ) # Draw the significance xMax, yMax = getXMaxYMax(hList) kwargs["opts"]["ymax"] = yMax*kwargs["opts"]["ymaxfactor"] kwargs["cutBox"] = {"cutValue": xMax, "fillColor": 16, "box": False, "line": True, "greaterThan": True} kwargs["cutBoxY"] = {"cutValue": yMax, "fillColor": 16, "box": False, "line": True, "greaterThan": True, "mainCanvas": True, "ratioCanvas": False} kwargs["moveLegend"]["dh"] = -0.15 for s in signalsList: p2.histoMgr.setHistoLegendLabelMany({ s: plots._legendLabels[s] }) if cutDir == ">=": name = saveName + "_Signif" + "GE" else: name = saveName + "_Signif" + "LE" plots.drawPlot(p2, name, **kwargs) SavePlot(p2, name, os.path.join(opts.saveDir), [".png"])#, ".pdf"] ) return
def GetRootHistos(datasetsMgr, histoList, regions): # Definition hPathDict = GetHistoPathDict(histoList, printList=True) rhDict = {} # For-loop: All Control Regions (CR) for region in regions: # Define labels lIncl = "%s-%s" % (region, "Inclusive") lGen = "%s-%s" % (region, "Genuine") lFake = "%s-%s" % (region, "Fake") # Get the desired histograms pIncl = plots.DataMCPlot(datasetsMgr, hPathDict[lIncl]) pGen = plots.DataMCPlot(datasetsMgr, hPathDict[lGen]) pFake = plots.DataMCPlot(datasetsMgr, hPathDict[lFake]) # Get the desired histograms p = plots.DataMCPlot(datasetsMgr, hPathDict[lIncl]) # Clone and Save the root histograms rhDict["TT-" + lIncl] = pIncl.histoMgr.getHisto( "TT").getRootHisto().Clone("TT-" + lIncl) rhDict["TT-" + lGen] = pGen.histoMgr.getHisto( "TT").getRootHisto().Clone("TT-" + lGen) rhDict["TT-" + lFake] = pFake.histoMgr.getHisto( "TT").getRootHisto().Clone("TT-" + lFake) rhDict["Data-" + lIncl] = pIncl.histoMgr.getHisto( "Data").getRootHisto().Clone("Data-" + lIncl) rhDict["EWK-" + lIncl] = pIncl.histoMgr.getHisto( "EWK").getRootHisto().Clone("EWK-" + lIncl) rhDict["QCD-" + lIncl] = pIncl.histoMgr.getHisto( "QCD").getRootHisto().Clone("QCD-" + lIncl) rhDict["SingleTop-" + lIncl] = pIncl.histoMgr.getHisto( "SingleTop").getRootHisto().Clone("SingleTop-" + lIncl) rhDict["SingleTop-" + lGen] = pGen.histoMgr.getHisto( "SingleTop").getRootHisto().Clone("SingleTop-" + lGen) rhDict["SingleTop-" + lFake] = pFake.histoMgr.getHisto( "SingleTop").getRootHisto().Clone("SingleTop-" + lFake) return rhDict
def PlotHistograms(datasetsMgr, histoName): # Get Histogram name and its kwargs saveName = histoName.rsplit("/")[-1] kwargs = GetHistoKwargs(saveName, opts) # Create the plot if "Data" in datasetsMgr.getAllDatasetNames(): p = plots.DataMCPlot(datasetsMgr, histoName, saveFormats=[]) else: if opts.normalizeToLumi: p = plots.MCPlot(datasetsMgr, histoName, normalizeToLumi=opts.intLumi, saveFormats=[]) elif opts.normalizeByCrossSection: p = plots.MCPlot(datasetsMgr, histoName, normalizeByCrossSection=True, saveFormats=[], **{}) elif opts.normalizeToOne: p = plots.MCPlot(datasetsMgr, histoName, normalizeToOne=True, saveFormats=[], **{}) else: raise Exception( "One of the options --normalizeToOne, --normalizeByCrossSection, --normalizeToLumi must be enabled (set to \"True\")." ) # Customise z-axis if 0: p.histoMgr.forEachHisto( lambda h: h.getRootHisto().GetZaxis().SetTitle(kwargs["zlabel"])) p.histoMgr.forEachHisto( lambda h: h.getRootHisto().GetZaxis().SetTitleOffset(1.3)) # Drawing style if 1: p.histoMgr.setHistoDrawStyleAll("AP") p.histoMgr.setHistoLegendStyleAll("LP") else: p.histoMgr.setHistoDrawStyleAll("HIST") p.histoMgr.setHistoLegendStyleAll("F") # Add dataset name on canvas # p.appendPlotObject(histograms.PlotText(0.18, 0.88, plots._legendLabels[opts.dataset], bold=True, size=22)) # Draw the plot plots.drawPlot(p, saveName, **kwargs) #the "**" unpacks the kwargs_ dictionary # Save the plots in custom list of saveFormats SavePlot(p, saveName, os.path.join(opts.saveDir), [".png", ".pdf"]) return
def createPlot(name, **kwargs): if mcOnly: plot = plots.MCPlot(datasets, name, normalizeToLumi=mcOnlyLumi, **kwargs) else: plot = plots.DataMCPlot(datasets, name, **kwargs) plot.histoMgr.removeHisto("EWK") return plot
def writeTransverseMass(datasets_lands): mt = plots.DataMCPlot(datasets_lands, "transverseMass") mt.histoMgr.forEachHisto(lambda h: h.getRootHisto().Rebin(10)) f = ROOT.TFile.Open(output, "RECREATE") mt_data = mt.histoMgr.getHisto("Data").getRootHisto().Clone("mt_data") mt_data.SetDirectory(f) mt_hw = mt.histoMgr.getHisto("TTToHplusBWB_M120").getRootHisto().Clone( "mt_hw") mt_hw.SetDirectory(f) mt_hh = mt.histoMgr.getHisto( "TTToHplusBHminusB_M120").getRootHisto().Clone("mt_hh") mt_hh.SetDirectory(f) f.Write() f.Close()
def GetRootHistos(datasetsMgr, histoList): hPathDict = GetHistoPathDict(histoList, printList=False) rhDict = {} # For-loop: All histograms for h in histoList: inclu, genuB, fakeB = GetHistoLabelTriplet(h) pIncl = plots.DataMCPlot(datasetsMgr, hPathDict[inclu]) pGenB = plots.DataMCPlot(datasetsMgr, hPathDict[genuB]) pFakeB = plots.DataMCPlot(datasetsMgr, hPathDict[fakeB]) # Define mapping keys: "Datasets-Region-Bin-Triplet" key1 = "Data-%s" % (inclu) key2 = "EWKGenuineB-%s" % (genuB) key3 = "EWKFakeB-%s" % (fakeB) key4 = "FakeB-%s" % (inclu) # Clone and Save the root histograms rhDict[key1] = pIncl.histoMgr.getHisto("Data").getRootHisto().Clone( "Data-" + h) rhDict[key2] = pGenB.histoMgr.getHisto("EWK").getRootHisto().Clone( "EWKGenuineB-" + h) rhDict[key3] = pFakeB.histoMgr.getHisto("EWK").getRootHisto().Clone( "EWKFakeB-" + h) rhDict[key4] = pIncl.histoMgr.getHisto("Data").getRootHisto().Clone( "FakeB-" + h) rhDict[key4].Add(rhDict[key2], -1) # For debugging: if 0: for k in rhDict: if "FakeB" not in k: continue fakeBResult.PrintTH1Info(rhDict[k]) return rhDict
def purityGraph(i, datasets, histo): inverted = plots.DataMCPlot(datasets, histo) # inverted.histoMgr.forEachHisto(lambda h: h.getRootHisto().Rebin(5)) inverted.histoMgr.forEachHisto( lambda h: h.setRootHisto(h.getRootHisto().Rebin( len(binning) - 1, h.getRootHisto().GetName(), array.array('d', binning)))) invertedData = inverted.histoMgr.getHisto("Data").getRootHisto().Clone( histo) invertedData.Scale(QCDInvertedNormalization["Inclusive"]) invertedEWK = inverted.histoMgr.getHisto("EWK").getRootHisto().Clone(histo) invertedEWK.Scale(QCDInvertedNormalization["InclusiveEWK"]) numerator = invertedData.Clone() numerator.SetName("numerator") numerator.Add(invertedEWK, -1) denominator = invertedData.Clone() denominator.SetName("denominator") numerator.Divide(denominator) purityGraph = ROOT.TGraphAsymmErrors(numerator) """ purity = ROOT.TEfficiency(numerator,denominator) purity.SetStatisticOption(ROOT.TEfficiency.kFNormal) collection = ROOT.TObjArray() collection.Add(purity) weights = [] weights.append(1) purityGraph = ROOT.TEfficiency.Combine(collection,"",len(weights),array.array("d",weights)) """ purityGraph.SetMarkerStyle(20 + i) purityGraph.SetMarkerColor(2 + i) if i == 3: purityGraph.SetMarkerColor(6) defaults = {"drawStyle": "EP", "legendStyle": "p"} return histograms.Histo(purityGraph, "Purity%s" % i, **defaults)
def Plot2dHistograms(datasetsMgr, histoName): Verbose("Plotting Data-MC Histograms") # Get Histogram name and its kwargs saveName = histoName.rsplit("/")[-1] kwargs = GetHistoKwargs(saveName, opts) # Create the 2d plot if opts.dataset == "Data": p = plots.DataMCPlot(datasetsMgr, histoName, saveFormats=[]) else: if opts.normalizeToLumi: p = plots.MCPlot(datasetsMgr, histoName, normalizeToLumi=opts.intLumi, saveFormats=[]) elif opts.normalizeByCrossSection: p = plots.MCPlot(datasetsMgr, histoName, normalizeByCrossSection=True, saveFormats=[], **{}) elif opts.normalizeToOne: p = plots.MCPlot(datasetsMgr, histoName, normalizeToOne=True, saveFormats=[], **{}) else: raise Exception("One of the options --normalizeToOne, --normalizeByCrossSection, --normalizeToLumi must be enabled (set to \"True\").") # Customise z-axis p.histoMgr.forEachHisto(lambda h: h.getRootHisto().GetZaxis().SetTitle(kwargs["zlabel"])) p.histoMgr.forEachHisto(lambda h: h.getRootHisto().GetZaxis().SetTitleOffset(1.3)) if kwargs.get("zmin") != None: zMin = float(kwargs.get("zmin")) p.histoMgr.forEachHisto(lambda h: h.getRootHisto().SetMinimum(zMin)) if kwargs.get("zmax") != None: zMax = float(kwargs.get("zmax")) p.histoMgr.forEachHisto(lambda h: h.getRootHisto().SetMaximum(zMax)) # Drawing style p.histoMgr.setHistoDrawStyleAll("COLZ") # Add dataset name on canvas p.appendPlotObject(histograms.PlotText(0.18, 0.88, plots._legendLabels[opts.dataset], bold=True, size=22)) # Draw the plot plots.drawPlot(p, saveName, **kwargs) #the "**" unpacks the kwargs_ dictionary # Save the plots in custom list of saveFormats SavePlot(p, saveName, os.path.join(opts.saveDir, opts.optMode, opts.folder, opts.dataset), [".png", ".pdf"] ) return
def TopSelectionHistograms(opts, datasetsMgr, analysisType): ''' Create data-MC comparison plot, with the default: - legend labels (defined in plots._legendLabels) - plot styles (defined in plots._plotStyles, and in styles) - drawing styles ('HIST' for MC, 'EP' for data) - legend styles ('L' for MC, 'P' for data) ''' Verbose("Plotting all topSelection histograms for %s" % analysisType) # Sanity check IsBaselineOrInverted(analysisType) # Definitions histoNames = getTopSelectionHistos(opts.histoLevel, analysisType) histoKwargs = {} saveFormats = [".png", ".pdf"] #[".C", ".png", ".pdf"] # General Settings if opts.mergeEWK: _moveLegend = {"dx": -0.1, "dy": 0.0, "dh": -0.15} else: _moveLegend = {"dx": -0.1, "dy": 0.0, "dh": 0.1} logY = True if logY: _opts1 = {"ymin": 1.0, "ymaxfactor": 10} else: _opts1 = {"ymin": 0.0, "ymaxfactor": 1.2} _opts2 = {"ymin": 0.0, "ymax": 2.0}, _kwargs = { "rebinX": 10, "rebinY": None, "ratioYlabel": "Data/MC", "ratio": False, "stackMCHistograms": True, "ratioInvert": False, "addMCUncertainty": False, "addLuminosityText": True, "addCmsText": True, "cmsExtraText": "Preliminary", "opts": _opts1, "opts2": _opts2, "log": logY, "errorBarsX": True, "moveLegend": _moveLegend, "cutBox": { "cutValue": 0.0, "fillColor": 16, "box": False, "line": False, "greaterThan": True }, "ylabel": "Events / %.0f", } # Create/Draw the plots for histoName in histoNames: histoKwargs[histoName] = _kwargs # For-loop: All histograms in list folder = "topSelection_" for histoName in histoNames: kwargs_ = histoKwargs[histoName] saveName = histoName.replace(folder + analysisType + "/", "") if opts.mcOnly: p = plots.MCPlot(datasetsMgr, histoName, normalizeToLumi=opts.intLumi, saveFormats=[]) kwargs_.pop("ratio", None) kwargs_.pop("ratioYlabel", None) kwargs_.pop("ratioInvert", None) kwargs_.pop("opts2", None) plots.drawPlot(p, saveName, **kwargs_) #the "**" unpacks the kwargs_ dictionary else: p = plots.DataMCPlot(datasetsMgr, histoName, saveFormats=[]) plots.drawPlot(p, saveName, **kwargs_) #the "**" unpacks the kwargs_ dictionary # Save plot in all formats SavePlot(p, histoName, os.path.join(opts.saveDir, "DataEwkSignal")) #SavePlot(p, histoName, os.path.join(opts.saveDir, analysisType) ) return
def PlotAndFitTemplates(datasetsMgr, histoName, inclusiveFolder, opts): Verbose("PlotAndFitTemplates()") # Variable definition bkgName = "QCD" genuineBFolder = inclusiveFolder + "EWKGenuineB" fakeBFolder = inclusiveFolder + "EWKFakeB" baselineHisto = "%s/%s" % (inclusiveFolder, "Baseline_" + histoName) invertedHisto = "%s/%s" % (inclusiveFolder, "Inverted_" + histoName) # Create the histograms pBaseline = plots.DataMCPlot(datasetsMgr, baselineHisto) pInverted = plots.DataMCPlot(datasetsMgr, invertedHisto) # Get the desired histograms (Baseline) Data_baseline = pBaseline.histoMgr.getHisto("Data").getRootHisto().Clone( "Baseline Data") #also legend entry name FakeB_baseline = pBaseline.histoMgr.getHisto("Data").getRootHisto().Clone( "Baseline " + bkgName) EWK_baseline = pBaseline.histoMgr.getHisto("EWK").getRootHisto().Clone( "Baseline EWK") # Get the desired histograms (Inverted) # Data_inverted = pInverted.histoMgr.getHisto("Data").getRootHisto().Clone("Inverted Data") #not needed FakeB_inverted = pInverted.histoMgr.getHisto("Data").getRootHisto().Clone( "Inverted " + bkgName) EWK_inverted = pInverted.histoMgr.getHisto("EWK").getRootHisto().Clone( "Inverted EWK") # Subtact EWK-M Cfrom Data (QCD = Data - EWK) FakeB_baseline.Add(EWK_baseline, -1) FakeB_inverted.Add(EWK_inverted, -1) # Rebin the EWK-MC histo (significant fit improvement - opposite effect for QCD fit) EWK_baseline.RebinX(2) EWK_inverted.RebinX(2) FakeB_inverted.RebinX(1) if 0: print "+" * 100 Print("FIXME: Optimal is 1 (i.e. bin width of 10 GeV/c^{2})") print "+" * 100 FakeB_inverted.RebinX(2) # Create the final plot object compareHistos = [EWK_baseline] p = plots.ComparisonManyPlot(FakeB_inverted, compareHistos, saveFormats=[]) # Apply styles p.histoMgr.forHisto("Inverted " + bkgName, styles.getFakeBStyle()) p.histoMgr.forHisto("Baseline EWK", styles.getAltEWKStyle()) # Set draw style p.histoMgr.setHistoDrawStyle("Inverted " + bkgName, "P") p.histoMgr.setHistoDrawStyle("Baseline EWK", "AP") # Set legend style p.histoMgr.setHistoLegendStyle("Inverted " + bkgName, "P") p.histoMgr.setHistoLegendStyle("Baseline EWK", "LP") # Set legend labels p.histoMgr.setHistoLegendLabelMany({ "Baseline EWK": "EWK", "Inverted " + bkgName: "QCD", }) #========================================================================================= # Set Minimizer Options #========================================================================================= ''' https://root.cern.ch/root/htmldoc/guides/users-guide/FittingHistograms.html#the-th1fit-method https://root.cern.ch/root/html/src/ROOT__Math__MinimizerOptions.h.html#a14deB ''' if 0: ROOT.Math.MinimizerOptions.SetDefaultMinimizer("Minuit", "Migrad") ROOT.Math.MinimizerOptions.SetDefaultStrategy( 1) # Speed = 0, Balance = 1, Robustness = 2 ROOT.Math.MinimizerOptions.SetDefaultMaxFunctionCalls( 5000) # set maximum of function calls ROOT.Math.MinimizerOptions.SetDefaultMaxIterations( 5000 ) # set maximum iterations (one iteration can have many function calls) if 0: ROOT.Math.MinimizerOptions.SetDefaultMinimizer("Minuit", "Simplex") ROOT.Math.MinimizerOptions.SetDefaultMinimizer("Minuit", "Minimize") ROOT.Math.MinimizerOptions.SetDefaultMinimizer("Minuit", "MigradImproved") ROOT.Math.MinimizerOptions.SetDefaultMinimizer("Minuit", "Scan") ROOT.Math.MinimizerOptions.SetDefaultMinimizer("Minuit", "Seek") ROOT.Math.MinimizerOptions.SetDefaultErrorDef( 1 ) # error definition (=1. for getting 1 sigma error for chi2 fits) ROOT.Math.MinimizerOptions.SetDefaultMaxFunctionCalls( 1000000) # set maximum of function calls ROOT.Math.MinimizerOptions.SetDefaultMaxIterations( 1000000 ) # set maximum iterations (one iteration can have many function calls) ROOT.Math.MinimizerOptions.SetDefaultPrecision( -1 ) # precision in the objective function calculation (value <= 0 means left to default) ROOT.Math.MinimizerOptions.SetDefaultPrintLevel( 1 ) # None = -1, Reduced = 0, Normal = 1, ExtraForProblem = 2, Maximum = 3 ROOT.Math.MinimizerOptions.SetDefaultTolerance( 1e-03 ) # Minuit/Minuit2 converge when the EDM is less a given tolerance. (default 1e-03) if 1: hLine = "=" * 45 title = "{:^45}".format("Minimizer Options") print "\t", hLine print "\t", title print "\t", hLine minOpt = ROOT.Math.MinimizerOptions() minOpt.Print() print "\t", hLine, "\n" #========================================================================================= # Start fit process #========================================================================================= binLabels = ["Inclusive"] moduleInfoString = opts.optMode #opts.dataEra + "_" + opts.searchMode + "_" + opts.optMode #========================================================================================= # Create templates (EWK fakes, EWK genuine, QCD; data template is created by manager) #========================================================================================= manager = QCDNormalization.QCDNormalizationManagerDefault( binLabels, opts.mcrab, moduleInfoString) Print( "Creating the normalization templates with appropriate template names", True) template_EWKFakeB_Baseline = manager.createTemplate( "EWKFakeB_Baseline") #fixme-unused template_EWKFakeB_Inverted = manager.createTemplate( "EWKFakeB_Inverted") #fixme-unused template_EWKInclusive_Baseline = manager.createTemplate( "EWKInclusive_Baseline") template_EWKInclusive_Inverted = manager.createTemplate( "EWKInclusive_Inverted") template_FakeB_Baseline = manager.createTemplate("QCD_Baseline") template_FakeB_Inverted = manager.createTemplate("QCD_Inverted") #======================================================================================== # EWK #========================================================================================= ''' Optimal fit (Chi2/D.O.F = 3.2) FITMIN ; 80 FITMAX : 800 BinWidth: 10 GeV/c^2 par3 : -3.9174e-01 (fixed) ''' Print("Setting the fit-function to the EWK template", False) FITMIN_EWK = 80 FITMAX_EWK = 800 par0 = [+7.1817e-01, 0.0, 1.0] # cb_norm par1 = [+1.7684e+02, 150.0, 200.0] # cb_mean par2 = [+2.7287e+01, 20.0, 40.0] # cb_sigma (fixed for chiSq=2) par3 = [-3.9174e-01, -1.0, 0.0] # cb_alpha (fixed for chiSq=2) par4 = [+2.5104e+01, 0.0, 50.0] # cb_n par5 = [+7.4724e-05, 0.0, 1.0] # expo_norm par6 = [-4.6848e-02, -1.0, 0.0] # expo_a par7 = [+2.1672e+02, 200.0, 250.0] # gaus_mean (fixed for chiSq=2) par8 = [+6.3201e+01, 20.0, 80.0] # gaus_sigma template_EWKInclusive_Baseline.setFitter( QCDNormalization.FitFunction("EWKFunction", boundary=0, norm=1, rejectPoints=0), FITMIN_EWK, FITMAX_EWK) template_EWKInclusive_Baseline.setDefaultFitParam( defaultInitialValue=None, defaultLowerLimit=[ par0[1], par1[1], par2[1], par3[0], par4[1], par5[1], par6[1], par7[1], par8[1] ], defaultUpperLimit=[ par0[2], par1[2], par2[2], par3[0], par4[2], par5[2], par6[2], par7[2], par8[2] ]) #========================================================================================= # QCD #========================================================================================= ''' Optimal fit (Chi2/D.O.F = 25.6) FITMIN : 80 FITMAX : 1000 BinWidth: 5 GeV/c^2 f_{QCD} : ~0.75118 +/- 0.00740 (data-driven plots looked great with this value) ''' Print("Setting the fit-function to the QCD template", False) FITMIN_QCD = 90 # 120 FITMAX_QCD = 1000 # 1000 bPtochos = False if bPtochos: par0 = [0.92, 0.0, 1.0] # lognorm_norm par1 = [220.00, 180.0, 500.0] # lognorm_mean par2 = [1.44, 0.4, 10.0] # lognorm_shape par3 = [0.0, 0.0, 1.0] # exp_const par4 = [-0.01, -2.0, 0.0] # exp_coeff par5 = [220.00, 100.0, 400.0] # gaus_mean par6 = [40.00, 0.0, 60.0] # gaus_sigma template_FakeB_Inverted.setFitter( QCDNormalization.FitFunction("QCDFunction", boundary=0, norm=1, rejectPoints=0), FITMIN_QCD, FITMAX_QCD) template_FakeB_Inverted.setDefaultFitParam( defaultInitialValue=[ par0[0], par1[0], par2[0], par3[0], par4[0], par5[0], par6[0] ], defaultLowerLimit=[ par0[1], par1[1], par2[1], par3[1], par4[1], par5[1], par6[1] ], defaultUpperLimit=[ par0[2], par1[2], par2[2], par3[2], par4[2], par5[2], par6[2] ]) else: # par0 = [9.2578e-01, 0.0 , 1.0] # lognorm_norm # par1 = [2.3662e+02, 200.0 , 1000.0] # lognorm_mean # par2 = [1.4436e+00, 0.5, 10.0] # lognorm_shape # par3 = [2.2575e+02, 100.0 , 500.0] # gaus_mean # par4 = [3.6716e+01, 0.0 , 60.0] # gaus_sigma par0 = [0.92, 0.0, 1.0] # lognorm_norm par1 = [220.00, 180.0, 500.0] # lognorm_mean par2 = [1.44, 0.4, 10.0] # lognorm_shape par3 = [220.00, 100.0, 400.0] # gaus_mean par4 = [40.00, 0.0, 60.0] # gaus_sigma template_FakeB_Inverted.setFitter( QCDNormalization.FitFunction("QCDFunctionAlt", boundary=0, norm=1, rejectPoints=0), FITMIN_QCD, FITMAX_QCD) template_FakeB_Inverted.setDefaultFitParam( defaultInitialValue=[par0[0], par1[0], par2[0], par3[0], par4[0]], defaultLowerLimit=[par0[1], par1[1], par2[1], par3[1], par4[1]], defaultUpperLimit=[par0[2], par1[2], par2[2], par3[2], par4[2]]) #========================================================================================= # Set histograms to the templates #========================================================================================= Print("Adding the appropriate histogram to each of the the templates", False) template_EWKFakeB_Baseline.setHistogram(EWK_baseline, "Inclusive") #fixme template_EWKFakeB_Inverted.setHistogram(EWK_inverted, "Inclusive") #fixme template_EWKInclusive_Baseline.setHistogram(EWK_baseline, "Inclusive") template_EWKInclusive_Inverted.setHistogram(EWK_inverted, "Inclusive") template_FakeB_Baseline.setHistogram(FakeB_baseline, "Inclusive") template_FakeB_Inverted.setHistogram(FakeB_inverted, "Inclusive") #========================================================================================= # Fit individual templates to histogram "Data_baseline", with custom fit options #========================================================================================= fitOptions = "R L W 0 Q" #"R B L W 0 Q M" FITMIN_DATA = 80 FITMAX_DATA = 1000 manager.calculateNormalizationCoefficients(Data_baseline, fitOptions, FITMIN_DATA, FITMAX_DATA) Verbose("Write the normalisation factors to a python file", True) fileName = os.path.join( opts.mcrab, "QCDInvertedNormalizationFactors%s.py" % (getModuleInfoString(opts))) manager.writeNormFactorFile(fileName, opts) # Not really needed to plot the histograms again if 1: saveName = histoName plots.drawPlot( p, saveName, **GetHistoKwargs(histoName)) #the "**" unpacks the kwargs_ SavePlot(p, saveName, os.path.join(opts.saveDir, "Fit", opts.optMode)) return
def DataMCHistograms(datasetsMgr, qcdDatasetName): Verbose("Plotting Data-MC Histograms") # Definitions histoNames = [] saveFormats = [".png"] #[".C", ".png", ".pdf"] # Get list of histograms dataPath = "ForDataDrivenCtrlPlots" allHistos = datasetsMgr.getDataset(datasetsMgr.getAllDatasetNames()[0]).getDirectoryContent(dataPath) histoList = [h for h in allHistos if "StandardSelections" in h] histoList.extend([h for h in allHistos if "AllSelections" in h]) histoList = [h for h in histoList if "_MCEWK" not in h] histoList = [h for h in histoList if "_Purity" not in h] histoPaths = [dataPath + "/" + h for h in histoList] # Get histogram<->kwargs dictionary histoKwargs = GetHistoKwargs(histoPaths, opts) # For-loop: All histograms in list for histoName in histoPaths: #if "Mass" not in histoName: # continue if "JetEtaPhi" in histoName: continue if opts.signalMass == 0: if "LdgTrijetMass" in histoName: continue if "LdgTetrajetMass" in histoName: continue if "Vs" in histoName: continue # Not used in this analysis (yet) if "MHT" in histoName: continue # By definition of the Inverted sample the following histos cannot agree! if "NBjets_" in histoName: continue if "BJetPt_" in histoName: continue if "_BJetEta_" in histoName: continue if "_BtagDiscriminator_" in histoName: continue kwargs_ = histoKwargs[histoName] saveName = histoName.replace("/", "_") # Create the plotting object p = plots.DataMCPlot(datasetsMgr, histoName, saveFormats=[]) # Apply QCD data-driven style if opts.signalMass != 0: signal = "ChargedHiggs_HplusTB_HplusToTB_M_%.0f" % opts.signalMass mHPlus = "%s" % int(opts.signalMass) p.histoMgr.forHisto(signal, styles.getSignalStyleHToTB_M(mHPlus)) #p.histoMgr.forHisto(opts.signalMass, styles.getSignalStyleHToTB()) if opts.mcQCD: pass else: p.histoMgr.forHisto(qcdDatasetName, styles.getAltQCDStyle()) p.histoMgr.setHistoDrawStyle(qcdDatasetName, "HIST") p.histoMgr.setHistoLegendStyle(qcdDatasetName, "F") if not opts.mcQCD: p.histoMgr.setHistoLegendLabelMany({ qcdDatasetName: "QCD (Data)", }) else: p.histoMgr.setHistoLegendLabelMany({ "QCD": "QCD (MC)", }) # Apply blinding of signal region if "blindingRangeString" in kwargs_: startBlind = float(kwargs_["blindingRangeString"].split("-")[1]) endBlind = float(kwargs_["blindingRangeString"].split("-")[0]) plots.partiallyBlind(p, maxShownValue=startBlind, minShownValue=endBlind, invert=True, moveBlindedText=kwargs_["moveBlindedText"]) # Draw and save the plot plots.drawPlot(p, saveName, **kwargs_) #the "**" unpacks the kwargs_ dictionary SavePlot(p, saveName, os.path.join(opts.saveDir, opts.optMode) ) return
def PlotHistogram(dsetMgr, histoName, opts): # Get kistogram argumetns kwargs = GetHistoKwargs(histoName, opts) saveName = histoName.replace(opts.folder + "/", "") # Create the plotting object (Data, "FakeB") p1 = plots.DataMCPlot(dsetMgr, histoName, saveFormats=[]) # Copy dataset manager before changing datasets. Keep only EWK (GenuineB) datasets datasetMgr = dsetMgr.deepCopy() datasetMgr.selectAndReorder(aux.GetListOfEwkDatasets()) # Create the MCPlot for the EWKGenuineB histograms if opts.useMC: p2 = plots.MCPlot(datasetMgr, histoName, normalizeToLumi=opts.intLumi, saveFormats=[]) else: histoNameGenuineB = histoName.replace(opts.folder, opts.folder + "EWKGenuineB") p2 = plots.MCPlot(datasetMgr, histoNameGenuineB, normalizeToLumi=opts.intLumi, saveFormats=[]) # Add the datasets to be included in the plot myStackList = [] # Data-driven FakeB background if not opts.useMC: hFakeB = p1.histoMgr.getHisto("FakeB").getRootHisto() hhFakeB = histograms.Histo(hFakeB, "FakeB", legendLabel="Fake-b") hhFakeB.setIsDataMC(isData=False, isMC=True) myStackList.append(hhFakeB) else: hQCD = p1.histoMgr.getHisto("QCD").getRootHisto() hhQCD = histograms.Histo(hQCD, "QCD", legendLabel="QCD") hhQCD.setIsDataMC(isData=False, isMC=True) myStackList.append(hhQCD) # EWK GenuineB background (Replace all EWK histos with GenuineB histos) ewkHistoList = [] # For-loop: All EWK datasets for dataset in aux.GetListOfEwkDatasets(): h = p2.histoMgr.getHisto(dataset).getRootHisto() hh = histograms.Histo(h, dataset, plots._legendLabels[dataset]) hh.setIsDataMC(isData=False, isMC=True) myStackList.append(hh) # Collision data hData = p1.histoMgr.getHisto("Data").getRootHisto() hhData = histograms.Histo(hData, "Data") hhData.setIsDataMC(isData=True, isMC=False) myStackList.insert(0, hhData) # Signal hSignal = p1.histoMgr.getHisto(opts.signal).getRootHisto() hhSignal = histograms.Histo(hSignal, opts.signal, plots._legendLabels[opts.signal]) hhSignal.setIsDataMC(isData=False, isMC=True) myStackList.insert(1, hhSignal) # Create the final plot by passing the histogram list p3 = plots.DataMCPlot2(myStackList, saveFormats=[]) p3.setLuminosity(opts.intLumi) p3.setDefaultStyles() # Apply blinding of data in Signal Region (After creating the plot) if "blindingRangeString" in kwargs: startBlind = float(kwargs["blindingRangeString"].split("-")[1]) endBlind = float(kwargs["blindingRangeString"].split("-")[0]) plots.partiallyBlind(p3, maxShownValue=startBlind, minShownValue=endBlind, invert=True, moveBlindedText=kwargs["moveBlindedText"]) # Draw and save the plot plots.drawPlot(p3, saveName, **kwargs) SavePlot(p3, saveName, os.path.join(opts.saveDir, opts.optMode), saveFormats = [".png", ".pdf"]) return
def PlotHistosAndCalculateTF(datasetsMgr, histoList, binLabels, opts): # Get the histogram customisations (keyword arguments) _kwargs = GetHistoKwargs(histoList[0]) # Get the root histos for all datasets and Control Regions (CRs) regions = ["SR", "VR", "CRone", "CRtwo"] rhDict = GetRootHistos(datasetsMgr, histoList, regions, binLabels) #========================================================================================= # Calculate the Transfer Factor (TF) and save to file #========================================================================================= manager = FakeBNormalization.FakeBNormalizationManager(binLabels, opts.mcrab, opts.optMode, verbose=False) if opts.inclusiveOnly: #manager.CalculateTransferFactor(binLabels[0], rhDict["CRone-FakeB"], rhDict["CRtwo-FakeB"]) binLabel = "Inclusive" manager.CalculateTransferFactor("Inclusive", rhDict["FakeB-CRone-Inclusive"], rhDict["FakeB-CRtwo-Inclusive"]) else: for bin in binLabels: manager.CalculateTransferFactor(bin, rhDict["FakeB-CRone-%s" % bin], rhDict["FakeB-CRtwo-%s" % bin]) # Get unique a style for each region for k in rhDict: dataset = k.split("-")[0] region = k.split("-")[1] styles.getABCDStyle(region).apply(rhDict[k]) if "FakeB" in k: styles.getFakeBStyle().apply(rhDict[k]) # sr.apply(rhDict[k]) # ========================================================================================= # Create the final plot object # ========================================================================================= rData_SR = rhDict["Data-SR-Inclusive"] rEWKGenuineB_SR = rhDict["EWK-SR-Inclusive-EWKGenuineB"] rBkgSum_SR = rhDict["FakeB-VR-Inclusive"].Clone("BkgSum-SR-Inclusive") rBkgSum_SR.Reset() if opts.inclusiveOnly: bin = "Inclusive" # Normalise the VR histogram with the Transfer Factor ( BkgSum = VR * (CR1/CR2) ) binHisto_VR = rhDict["FakeB-VR-%s" % (bin)] VRtoSR_TF = manager.GetTransferFactor(bin) Print( "Applying TF = %s%0.6f%s to VR shape" % (ShellStyles.NoteStyle(), VRtoSR_TF, ShellStyles.NormalStyle()), True) binHisto_VR.Scale(VRtoSR_TF) # Add the normalised histogram to the final Inclusive SR (predicted) histo rBkgSum_SR.Add(binHisto_VR, +1) else: # For-loop: All bins for i, bin in enumerate(binLabels, 1): if bin == "Inclusive": continue # Normalise the VR histogram with the Transfer Factor ( BkgSum = VR * (CR1/CR2) ) binHisto_VR = rhDict["FakeB-VR-%s" % (bin)] VRtoSR_TF = manager.GetTransferFactor(bin) Print( "Applying TF = %s%0.6f%s to VR shape" % (ShellStyles.NoteStyle(), VRtoSR_TF, ShellStyles.NormalStyle()), i == 1) binHisto_VR.Scale(VRtoSR_TF) # Add the normalised histogram to the final Inclusive SR (predicted) histo rBkgSum_SR.Add(binHisto_VR, +1) #Print("Got Verification Region (VR) shape %s%s%s" % (ShellStyles.NoteStyle(), rFakeB_VR.GetName(), ShellStyles.NormalStyle()), True) # Normalise the VR histogram with the Transfer Factor ( BkgSum = VR * (CR1/CR2) ) #VRtoSR_TF = manager.GetTransferFactor("Inclusive") #Print("Applying TF = %s%0.6f%s to VR shape" % (ShellStyles.NoteStyle(), VRtoSR_TF, ShellStyles.NormalStyle()), True) #rBkgSum_SR.Scale(VRtoSR_TF) # Plot histograms if opts.altPlot: # Add the SR EWK Genuine-b to the SR FakeB ( BkgSum = [FakeB] + [GenuineB-MC] = [VR * (CR1/CR2)] + [GenuineB-MC] ) rBkgSum_SR.Add(rEWKGenuineB_SR, +1) # Change style styles.getGenuineBStyle().apply(rBkgSum_SR) # Remove unsupported settings of kwargs _kwargs["stackMCHistograms"] = False _kwargs["addLuminosityText"] = False # Create the plot p = plots.ComparisonManyPlot(rData_SR, [rBkgSum_SR], saveFormats=[]) # Set draw / legend style p.histoMgr.setHistoDrawStyle("Data-SR-Inclusive", "P") p.histoMgr.setHistoLegendStyle("Data-SR-Inclusive", "LP") p.histoMgr.setHistoDrawStyle("BkgSum-SR-Inclusive", "HIST") p.histoMgr.setHistoLegendStyle("BkgSum-SR-Inclusive", "F") # Set legend labels p.histoMgr.setHistoLegendLabelMany({ "Data-SR": "Data", "BkgSum-SR": "Fake-b + Gen-b", }) else: # Create empty histogram stack list myStackList = [] # Signal p2 = plots.DataMCPlot(datasetsMgr, "ForTestQGLR/QGLR_SR/QGLR_SRInclusive", saveFormats=[]) hSignal_800 = p2.histoMgr.getHisto( 'ChargedHiggs_HplusTB_HplusToTB_M_800').getRootHisto() hhSignal_800 = histograms.Histo( hSignal_800, 'ChargedHiggs_HplusTB_HplusToTB_M_800', "H^{+} m_{H^+}=800 GeV") hhSignal_800.setIsDataMC(isData=False, isMC=True) myStackList.append(hhSignal_800) hSignal_250 = p2.histoMgr.getHisto( 'ChargedHiggs_HplusTB_HplusToTB_M_250').getRootHisto() hhSignal_250 = histograms.Histo( hSignal_250, 'ChargedHiggs_HplusTB_HplusToTB_M_250', "H^{+} m_{H^+}=250 GeV" ) #plots._legendLabels['ChargedHiggs_HplusTB_HplusToTB_M_250']) hhSignal_250.setIsDataMC(isData=False, isMC=True) #myStackList.append(hhSignal_250) hSignal_500 = p2.histoMgr.getHisto( 'ChargedHiggs_HplusTB_HplusToTB_M_500').getRootHisto() hhSignal_500 = histograms.Histo( hSignal_500, 'ChargedHiggs_HplusTB_HplusToTB_M_500', "H^{+} m_{H^+}=500 GeV" ) #plots._legendLabels['ChargedHiggs_HplusTB_HplusToTB_M_500']) hhSignal_500.setIsDataMC(isData=False, isMC=True) #myStackList.append(hhSignal_500) hSignal_1000 = p2.histoMgr.getHisto( 'ChargedHiggs_HplusTB_HplusToTB_M_1000').getRootHisto() hhSignal_1000 = histograms.Histo( hSignal_1000, 'ChargedHiggs_HplusTB_HplusToTB_M_1000', "H^{+} m_{H^+}=1000 GeV" ) #plots._legendLabels['ChargedHiggs_HplusTB_HplusToTB_M_500']) hhSignal_1000.setIsDataMC(isData=False, isMC=True) #myStackList.append(hhSignal_1000) # Add the FakeB data-driven background to the histogram list hFakeB = histograms.Histo(rBkgSum_SR, "FakeB", "Fake-b") hFakeB.setIsDataMC(isData=False, isMC=True) myStackList.append(hFakeB) # Add the EWKGenuineB MC background to the histogram list hGenuineB = histograms.Histo(rEWKGenuineB_SR, "GenuineB", "EWK Genuine-b") hGenuineB.setIsDataMC(isData=False, isMC=True) myStackList.append(hGenuineB) # Add the collision datato the histogram list hData = histograms.Histo(rData_SR, "Data", "Data") hData.setIsDataMC(isData=True, isMC=False) myStackList.insert(0, hData) p = plots.DataMCPlot2(myStackList, saveFormats=[]) p.setLuminosity(opts.intLumi) p.setDefaultStyles() # Draw the plot and save it hName = "test" plots.drawPlot(p, hName, **_kwargs) SavePlot(p, hName, os.path.join(opts.saveDir, opts.optMode), saveFormats=[".png", ".pdf"]) #========================================================================================== # Calculate Cut-Flow Efficiency #========================================================================================== kwargs = { "rebinX": 1, "xlabel": "QGLR", "ylabel": "Significance / %.02f ", "opts": { "ymin": 0.0, "ymaxfactor": 1.3 }, "createLegend": { "x1": 0.55, "y1": 0.70, "x2": 0.92, "y2": 0.92 }, # "cutBox" : {"cutValue": 0.0, "fillColor" : 16, "box": False, "line": False, "greaterThan": True}, } efficiencyList = [] xValues = [] yValues_250 = [] yValues_500 = [] yValues_800 = [] yValues_1000 = [] yValues_Bkg = [] nBins = hSignal_250.GetNbinsX() + 1 hBkg = p.histoMgr.getHisto( "ChargedHiggs_HplusTB_HplusToTB_M_800").getRootHisto().Clone("Bkg") hBkg.Reset() # Bkg: FakeB + Genuine B hBkg.Add(hFakeB.getRootHisto(), +1) hBkg.Add(hGenuineB.getRootHisto(), +1) for i in range(0, nBins): # Cut value cut = hSignal_250.GetBinCenter(i) passed_250 = hSignal_250.Integral(i, hSignal_250.GetXaxis().GetNbins()) passed_500 = hSignal_500.Integral(i, hSignal_500.GetXaxis().GetNbins()) passed_800 = hSignal_800.Integral(i, hSignal_800.GetXaxis().GetNbins()) passed_1000 = hSignal_1000.Integral(i, hSignal_1000.GetXaxis().GetNbins()) passed_Bkg = hBkg.Integral(i, hBkg.GetXaxis().GetNbins()) total_250 = hSignal_250.Integral() total_500 = hSignal_500.Integral() total_800 = hSignal_800.Integral() total_1000 = hSignal_1000.Integral() total_Bkg = hBkg.Integral() eff_250 = float(passed_250) / total_250 eff_500 = float(passed_500) / total_500 eff_800 = float(passed_800) / total_800 eff_1000 = float(passed_1000) / total_1000 eff_Bkg = float(passed_Bkg) / total_Bkg xValues.append(cut) yValues_250.append(eff_250) yValues_500.append(eff_500) yValues_800.append(eff_800) yValues_1000.append(eff_1000) yValues_Bkg.append(eff_Bkg) # Create the Efficiency Plot tGraph_250 = ROOT.TGraph(len(xValues), array.array("d", xValues), array.array("d", yValues_250)) tGraph_500 = ROOT.TGraph(len(xValues), array.array("d", xValues), array.array("d", yValues_500)) tGraph_800 = ROOT.TGraph(len(xValues), array.array("d", xValues), array.array("d", yValues_800)) tGraph_1000 = ROOT.TGraph(len(xValues), array.array("d", xValues), array.array("d", yValues_1000)) tGraph_Bkg = ROOT.TGraph(len(xValues), array.array("d", xValues), array.array("d", yValues_Bkg)) styles.getSignalStyleHToTB_M("200").apply(tGraph_250) styles.getSignalStyleHToTB_M("500").apply(tGraph_500) styles.getSignalStyleHToTB_M("800").apply(tGraph_800) styles.getSignalStyleHToTB_M("1000").apply(tGraph_1000) styles.getQCDLineStyle().apply(tGraph_Bkg) drawStyle = "CPE" effGraph_250 = histograms.HistoGraph(tGraph_250, "H^{+} m_{H^{+}} = 250 GeV", "lp", drawStyle) effGraph_500 = histograms.HistoGraph(tGraph_500, "H^{+} m_{H^{+}} = 500 GeV", "lp", drawStyle) effGraph_800 = histograms.HistoGraph(tGraph_800, "H^{+} m_{H^{+}} = 800 GeV", "lp", drawStyle) effGraph_1000 = histograms.HistoGraph(tGraph_1000, "H^{+} m_{H^{+}} = 1000 GeV", "lp", drawStyle) effGraph_Bkg = histograms.HistoGraph(tGraph_Bkg, "Bkg", "lp", drawStyle) efficiencyList.append(effGraph_250) efficiencyList.append(effGraph_500) efficiencyList.append(effGraph_800) efficiencyList.append(effGraph_1000) efficiencyList.append(effGraph_Bkg) # Efficiency plot pE = plots.PlotBase(efficiencyList, saveFormats=["pdf"]) pE.createFrame("QGLR_Efficiency") pE.setEnergy("13") pE.getFrame().GetYaxis().SetLabelSize(18) pE.getFrame().GetXaxis().SetLabelSize(20) pE.getFrame().GetYaxis().SetTitle("Efficiency / 0.01") pE.getFrame().GetXaxis().SetTitle("QGLR Cut") # Add Standard Texts to plot histograms.addStandardTexts() # Customise Legend moveLegend = {"dx": -0.50, "dy": -0.5, "dh": -0.1} pE.setLegend(histograms.moveLegend(histograms.createLegend(), **moveLegend)) pE.draw() # plots.drawPlot(pE, "QGLR_Efficiency", **kwargs) SavePlot(pE, "QGLR_Efficiency", os.path.join(opts.saveDir, opts.optMode), saveFormats=[".png", ".pdf"]) #========================================================================================== # Calculate Significance #========================================================================================== SignalName = "ChargedHiggs_HplusTB_HplusToTB_M_800" hSignif_250 = p.histoMgr.getHisto(SignalName).getRootHisto().Clone( SignalName) hSignif_500 = p.histoMgr.getHisto(SignalName).getRootHisto().Clone( SignalName) hSignif_800 = p.histoMgr.getHisto(SignalName).getRootHisto().Clone( SignalName) hSignif_1000 = p.histoMgr.getHisto(SignalName).getRootHisto().Clone( SignalName) hSignif_250.Reset() hSignif_500.Reset() hSignif_800.Reset() hSignif_1000.Reset() hBkg = p.histoMgr.getHisto(SignalName).getRootHisto().Clone("Bkg") hBkg.Reset() # Bkg: FakeB + Genuine B hBkg.Add(hFakeB.getRootHisto(), +1) hBkg.Add(hGenuineB.getRootHisto(), +1) nBins = hSignif_250.GetNbinsX() + 1 # For-loop: All histo bins for i in range(1, nBins + 1): sigmaB = ROOT.Double(0) b = hBkg.IntegralAndError(i, nBins, sigmaB) s_250 = hSignal_250.Integral(i, nBins) s_500 = hSignal_500.Integral(i, nBins) s_800 = hSignal_800.Integral(i, nBins) s_1000 = hSignal_1000.Integral(i, nBins) # Calculate significance signif_250 = stat.significance(s_250, b, sigmaB, option="Simple") #Asimov") signif_500 = stat.significance(s_500, b, sigmaB, option="Simple") #Asimov") signif_800 = stat.significance(s_800, b, sigmaB, option="Simple") #Asimov") signif_1000 = stat.significance(s_1000, b, sigmaB, option="Simple") #"Asimov") # Set signif for this bin hSignif_250.SetBinContent(i, signif_250) hSignif_500.SetBinContent(i, signif_500) hSignif_800.SetBinContent(i, signif_800) hSignif_1000.SetBinContent(i, signif_1000) # Apply style s_250 = styles.getSignalStyleHToTB_M("200") s_250.apply(hSignif_250) s_500 = styles.getSignalStyleHToTB_M("500") s_500.apply(hSignif_500) s_800 = styles.getSignalStyleHToTB_M("800") s_800.apply(hSignif_800) s_1000 = styles.getSignalStyleHToTB_M("1000") s_1000.apply(hSignif_1000) hList = [] hList.append(hSignif_250) hList.append(hSignif_500) hList.append(hSignif_800) hList.append(hSignif_1000) hSignif_250.SetName("H^{+} m_{H^{+}} = 250 GeV") hSignif_500.SetName("H^{+} m_{H^{+}} = 500 GeV") hSignif_800.SetName("H^{+} m_{H^{+}} = 800 GeV") hSignif_1000.SetName("H^{+} m_{H^{+}} = 1000 GeV") pS = plots.PlotBase(hList, saveFormats=["png", "pdf"]) pS.setLuminosity(opts.intLumi) # Drawing style pS.histoMgr.setHistoDrawStyleAll("HIST") pS.histoMgr.setHistoLegendStyleAll("L") pS.histoMgr.forEachHisto(lambda h: h.getRootHisto().SetMarkerSize(1.0)) pS.histoMgr.forEachHisto( lambda h: h.getRootHisto().SetLineStyle(ROOT.kSolid)) pS.histoMgr.forEachHisto( lambda h: h.getRootHisto().SetMarkerStyle(ROOT.kFullCircle)) # Draw the plot name = "QGLR_Signif" + "GE" plots.drawPlot(pS, name, **kwargs) SavePlot(pS, name, os.path.join(opts.saveDir, opts.optMode), saveFormats=[".png", ".pdf"]) #========================================================================================= # Calculate the Transfer Factor (TF) and save to file #========================================================================================= Verbose("Write the normalisation factors to a python file", True) fileName = os.path.join( opts.mcrab, "FakeBTransferFactors%s.py" % (getModuleInfoString(opts))) manager.writeNormFactorFile(fileName, opts) return
def GetHistoGraphs(datasetsMgr, folder, hName): # Get histogram customisations _kwargs = GetHistoKwargs(opts) # Get histos (Data, EWK) for Inclusive p1 = plots.DataMCPlot(datasetsMgr, hName, saveFormats=[]) kwargs = copy.deepcopy(_kwargs) kwargs["opts"] = {"ymin": 1.0, "ymaxfactor": 10.0} kwargs["xlabelsize"] = 10 kwargs["ratio"] = False plots.drawPlot(p1, hName, **kwargs) SavePlot(p1, hName, os.path.join(opts.saveDir, opts.optMode), saveFormats=[".C", ".png", ".pdf"]) # Clone histograms histoList = [] graphList = [] hgList = [] # Append some bkg samples as well opts.datasets = opts.signal if not opts.acceptance: opts.datasets.extend(opts.backgrounds) for d in opts.datasets: h = p1.histoMgr.getHisto(d).getRootHisto().Clone(d) histoList.append(h) # Create the Efficiency histos for i, h in enumerate(histoList, 1): if opts.efficiency: histo = GetEfficiencyHisto(histoList[i - 1], opts.refCounter, _kwargs, printValues=True, hideZeros=True) histo.SetName("Efficiency_%d" % (i)) elif opts.events: histo = GetEventsHisto(histoList[i - 1], opts.refCounter, _kwargs, printValues=True, hideZeros=True) histo.SetName("Events_%d" % (i)) elif opts.acceptance: histo = GetAcceptanceHisto(histoList[i - 1], _kwargs, printValues=True, hideZeros=True) histo.SetName("Acceptance_%d" % (i)) # Convert histos to TGraph (don't do it for acceptance to get better positioning of markers wrt x-axis!) if not opts.acceptance: tgraph = convertHisto2TGraph(histo, printValues=False) else: tgraph = histo # Apply random histo styles and append if "charged" in h.GetName().lower(): s = styles.getSignalStyleHToTB_M(h.GetName().split("M_")[-1]) s.apply(tgraph) if "QCD" in h.GetName(): styles.fakeBStyle.apply(tgraph) if "EWK" in h.GetName(): s = styles.ttStyle.apply(tgraph) # Append to list graphList.append(tgraph) # Create histoGraph object htgraph = histograms.HistoGraph( tgraph, plots._legendLabels[opts.signal[i - 1]], "LP", "LP") # Append to list hgList.append(htgraph) return hgList, _kwargs
def PlotHistograms(datasetsMgr, histoName): # Get Histogram name and its kwargs rootHistos = [] bdiscList = ["Loose", "Medium"] saveName = histoName.rsplit("/")[-1] kwargs = GetHistoKwargs(saveName, opts) myBdiscs = [] histoName = histoName.replace(opts.folder, "") stylesList = [styles.FakeBStyle1, styles.FakeBStyle3, styles.FakeBStyle2, styles.FakeBStyle4] #stylesList = [styles.fakeBLineStyle1, styles.FakeBStyle2, styles.FakeBStyle3, styles.FakeBStyle4] # For-loop: All histograms in all regions for bdisc in bdiscList: hName_ = histoName.replace(opts.refBdisc, bdisc) hName = opts.folder + "/" + hName_ if "Data" in datasetsMgr.getAllDatasetNames(): p = plots.DataMCPlot(datasetsMgr, hName, saveFormats=[]) else: p = plots.MCPlot(datasetsMgr, hName, normalizeToLumi=opts.intLumi, saveFormats=[]) # Append (non-empty) dataset ROOT histos to a list for plotting h = p.histoMgr.getHisto(opts.dataset).getRootHisto() if h.GetEntries() > 0: h.SetName(bdisc) rootHistos.append(h) myBdiscs.append(bdisc) # Create a comparison plot for a given dataset in all CRs if len(rootHistos) < 2: Print("Cannot plot comparison due to too few non-empty histograms present (=%i)" % (len(rootHistos)), False) return # Move ref histo to top of rootHisto list for rh in rootHistos: if opts.refBdisc in rh.GetName(): s = rootHistos.pop( rootHistos.index(rh) ) #rootHistos.insert(0, s) rootHistos.insert(len(rootHistos), s) # Draw the comparison plot (first argument the reference histo for ratio purposes) p = plots.ComparisonManyPlot(rootHistos[-1], rootHistos[:-1], saveFormats=[]) # p = plots.ComparisonManyPlot(rootHistos[0], rootHistos[1:], saveFormats=[]) p.setLuminosity(opts.intLumi) if opts.normalizeToOne: p.histoMgr.forEachHisto(lambda h: h.getRootHisto().Scale(1.0/h.getRootHisto().Integral())) # Apply drawing/legend styles for i, bdisc in enumerate(myBdiscs, 0): stylesList[i].apply(p.histoMgr.getHisto(bdisc).getRootHisto()) if bdisc == opts.refBdisc: p.histoMgr.setHistoDrawStyle(bdisc, "AP") p.histoMgr.setHistoLegendStyle(bdisc,"LP") else: p.histoMgr.setHistoDrawStyle(bdisc, "AP") p.histoMgr.setHistoLegendStyle(bdisc, "LP") #p.histoMgr.setHistoDrawStyle(bdisc, "HIST") #p.histoMgr.setHistoLegendStyle(bdisc, "F") # Add dataset name on canvas p.appendPlotObject(histograms.PlotText(0.18, 0.88, plots._legendLabels[opts.dataset], bold=True, size=22)) #p.appendPlotObject(histograms.PlotText(0.18, 0.88, plots._legendLabels[opts.dataset + " (%s)" % ], bold=True, size=22)) # Set legend labels p.histoMgr.setHistoLegendLabelMany({ "Loose" : "Loose (%s)" % (GetCRLabel(histoName)), "Medium": "Medium (%s)" % (GetCRLabel(histoName)), }) # Draw the plot plots.drawPlot(p, saveName, **kwargs) #the "**" unpacks the kwargs_ dictionary # Save the plots in custom list of saveFormats SavePlot(p, saveName, os.path.join(opts.saveDir), [".png", ".pdf"] ) return
def PlotComparison(datasetsMgr1, datasetsMgr2, datasetsMgr3, hBaseline, hInverted, ext): # Create corresponding paths for GenuineB and FakeB histograms (not only Inclusive) hBaseline_Inclusive = hBaseline #no extra string hInverted_Inclusive = hInverted #no extra string hBaseline_GenuineB = hBaseline_Inclusive.replace( opts.folder, opts.folder + "EWKGenuineB") hInverted_GenuineB = hInverted_Inclusive.replace( opts.folder, opts.folder + "EWKGenuineB") hBaseline_FakeB = hBaseline_Inclusive.replace(opts.folder, opts.folder + "EWKFakeB") hInverted_FakeB = hInverted_Inclusive.replace(opts.folder, opts.folder + "EWKFakeB") # Create the histograms in the Baseline (SR) and Inverted (CR) regions pBaseline_Inclusive1 = plots.DataMCPlot(datasetsMgr1, hBaseline_Inclusive) pBaseline_GenuineB1 = plots.DataMCPlot(datasetsMgr1, hBaseline_GenuineB) pBaseline_FakeB1 = plots.DataMCPlot(datasetsMgr1, hBaseline_FakeB) pInverted_Inclusive1 = plots.DataMCPlot(datasetsMgr1, hInverted_Inclusive) pInverted_GenuineB1 = plots.DataMCPlot(datasetsMgr1, hInverted_GenuineB) pInverted_FakeB1 = plots.DataMCPlot(datasetsMgr1, hInverted_FakeB) pBaseline_Inclusive2 = plots.DataMCPlot(datasetsMgr2, hBaseline_Inclusive) pBaseline_GenuineB2 = plots.DataMCPlot(datasetsMgr2, hBaseline_GenuineB) pBaseline_FakeB2 = plots.DataMCPlot(datasetsMgr2, hBaseline_FakeB) pInverted_Inclusive2 = plots.DataMCPlot(datasetsMgr2, hInverted_Inclusive) pInverted_GenuineB2 = plots.DataMCPlot(datasetsMgr2, hInverted_GenuineB) pInverted_FakeB2 = plots.DataMCPlot(datasetsMgr2, hInverted_FakeB) pBaseline_Inclusive3 = plots.DataMCPlot(datasetsMgr3, hBaseline_Inclusive) pBaseline_GenuineB3 = plots.DataMCPlot(datasetsMgr3, hBaseline_GenuineB) pBaseline_FakeB3 = plots.DataMCPlot(datasetsMgr3, hBaseline_FakeB) pInverted_Inclusive3 = plots.DataMCPlot(datasetsMgr3, hInverted_Inclusive) pInverted_GenuineB3 = plots.DataMCPlot(datasetsMgr3, hInverted_GenuineB) pInverted_FakeB3 = plots.DataMCPlot(datasetsMgr3, hInverted_FakeB) # Extract the correct SR and CR histograms baseline_Data1 = pBaseline_Inclusive1.histoMgr.getHisto( "Data").getRootHisto().Clone("Baseline-Data1") baseline_EWKGenuineB1 = pBaseline_GenuineB1.histoMgr.getHisto( "EWK").getRootHisto().Clone("Baseline-EWKGenuineB1") baseline_EWKFakeB1 = pBaseline_FakeB1.histoMgr.getHisto( "EWK").getRootHisto().Clone("Baseline-EWKFakeB1") inverted_Data1 = pInverted_Inclusive1.histoMgr.getHisto( "Data").getRootHisto().Clone("Inverted-Data1") inverted_EWKGenuineB1 = pInverted_GenuineB1.histoMgr.getHisto( "EWK").getRootHisto().Clone("Inverted-EWKGenuineB1") inverted_EWKFakeB1 = pInverted_FakeB1.histoMgr.getHisto( "EWK").getRootHisto().Clone("Inverted-EWKFakeB1") baseline_Data2 = pBaseline_Inclusive2.histoMgr.getHisto( "Data").getRootHisto().Clone("Baseline-Data2") baseline_EWKGenuineB2 = pBaseline_GenuineB2.histoMgr.getHisto( "EWK").getRootHisto().Clone("Baseline-EWKGenuineB2") baseline_EWKFakeB2 = pBaseline_FakeB2.histoMgr.getHisto( "EWK").getRootHisto().Clone("Baseline-EWKFakeB2") inverted_Data2 = pInverted_Inclusive2.histoMgr.getHisto( "Data").getRootHisto().Clone("Inverted-Data2") inverted_EWKGenuineB2 = pInverted_GenuineB2.histoMgr.getHisto( "EWK").getRootHisto().Clone("Inverted-EWKGenuineB2") inverted_EWKFakeB2 = pInverted_FakeB2.histoMgr.getHisto( "EWK").getRootHisto().Clone("Inverted-EWKFakeB2") baseline_Data3 = pBaseline_Inclusive3.histoMgr.getHisto( "Data").getRootHisto().Clone("Baseline-Data3") baseline_EWKGenuineB3 = pBaseline_GenuineB3.histoMgr.getHisto( "EWK").getRootHisto().Clone("Baseline-EWKGenuineB3") baseline_EWKFakeB3 = pBaseline_FakeB3.histoMgr.getHisto( "EWK").getRootHisto().Clone("Baseline-EWKFakeB3") inverted_Data3 = pInverted_Inclusive3.histoMgr.getHisto( "Data").getRootHisto().Clone("Inverted-Data3") inverted_EWKGenuineB3 = pInverted_GenuineB3.histoMgr.getHisto( "EWK").getRootHisto().Clone("Inverted-EWKGenuineB3") inverted_EWKFakeB3 = pInverted_FakeB3.histoMgr.getHisto( "EWK").getRootHisto().Clone("Inverted-EWKFakeB3") # FakeB = Data -EWKGenuineB baseline_FakeB1 = baseline_Data1.Clone("Baseline-FakeB1") inverted_FakeB1 = inverted_Data1.Clone("Inverted-FakeB1") baseline_FakeB2 = baseline_Data2.Clone("Baseline-FakeB2") inverted_FakeB2 = inverted_Data2.Clone("Inverted-FakeB2") baseline_FakeB3 = baseline_Data3.Clone("Baseline-FakeB3") inverted_FakeB3 = inverted_Data3.Clone("Inverted-FakeB3") # Subtract the EWK GenuineB baseline_FakeB1.Add(baseline_EWKGenuineB1, -1) inverted_FakeB1.Add(inverted_EWKGenuineB1, -1) baseline_FakeB2.Add(baseline_EWKGenuineB2, -1) inverted_FakeB2.Add(inverted_EWKGenuineB2, -1) baseline_FakeB3.Add(baseline_EWKGenuineB3, -1) inverted_FakeB3.Add(inverted_EWKGenuineB3, -1) # Normalize histograms to unit area if opts.normaliseToOne: baseline_FakeB1.Scale(1.0 / baseline_FakeB1.Integral()) inverted_FakeB1.Scale(1.0 / inverted_FakeB1.Integral()) baseline_FakeB2.Scale(1.0 / baseline_FakeB2.Integral()) inverted_FakeB2.Scale(1.0 / inverted_FakeB2.Integral()) baseline_FakeB3.Scale(1.0 / baseline_FakeB3.Integral()) inverted_FakeB3.Scale(1.0 / inverted_FakeB3.Integral()) # Create the final plot object if ext == "CR1" or ext == "SR": p = plots.ComparisonManyPlot(baseline_FakeB1, [baseline_FakeB2, baseline_FakeB3], saveFormats=[]) elif ext == "CR2" or ext == "VR": p = plots.ComparisonManyPlot(inverted_FakeB1, [inverted_FakeB2, inverted_FakeB3], saveFormats=[]) else: raise Exception("Unexpected extension %s" % (ext)) p.setLuminosity(opts.intLumi) # Get the BDT cut values from the multicrab name BDT1 = find_between(opts.mcrab1, "MVAm1p00to", "_").replace("p", ".") BDT2 = find_between(opts.mcrab2, "MVAm1p00to", "_").replace("p", ".") BDT3 = find_between(opts.mcrab3, "MVAm1p00to", "_").replace("p", ".") # Apply histogram styles if ext == "CR1" or ext == "SR": p.histoMgr.forHisto("Baseline-FakeB1", styles.getFakeBLineStyle() ) # getABCDStyle("SR") , getABCDStyle("VR") p.histoMgr.forHisto("Baseline-FakeB2", styles.genuineBAltStyle) p.histoMgr.forHisto("Baseline-FakeB3", styles.getABCDStyle("SR")) # Set drawing style p.histoMgr.setHistoDrawStyle("Baseline-FakeB1", "HIST") p.histoMgr.setHistoDrawStyle("Baseline-FakeB2", "AP") p.histoMgr.setHistoDrawStyle("Baseline-FakeB3", "AP") # Set legend styles p.histoMgr.setHistoLegendStyle("Baseline-FakeB1", "L") p.histoMgr.setHistoLegendStyle("Baseline-FakeB2", "LP") p.histoMgr.setHistoLegendStyle("Baseline-FakeB3", "LP") # Set legend labels p.histoMgr.setHistoLegendLabelMany({ "Baseline-FakeB1": "%s (BDT < %s)" % (ext, BDT1), "Baseline-FakeB2": "%s (BDT < %s)" % (ext, BDT2), "Baseline-FakeB3": "%s (BDT < %s)" % (ext, BDT3), }) else: p.histoMgr.forHisto("Inverted-FakeB1", styles.getFakeBLineStyle()) p.histoMgr.forHisto("Inverted-FakeB2", styles.genuineBAltStyle) p.histoMgr.forHisto("Inverted-FakeB3", styles.getABCDStyle("SR")) # Set drawing styles p.histoMgr.setHistoDrawStyle("Inverted-FakeB1", "HIST") p.histoMgr.setHistoDrawStyle("Inverted-FakeB2", "AP") p.histoMgr.setHistoDrawStyle("Inverted-FakeB3", "AP") # Set legend styles p.histoMgr.setHistoLegendStyle("Inverted-FakeB1", "L") p.histoMgr.setHistoLegendStyle("Inverted-FakeB2", "LP") p.histoMgr.setHistoLegendStyle("Inverted-FakeB3", "LP") # Set legend labels p.histoMgr.setHistoLegendLabelMany({ "Inverted-FakeB1": "%s (BDT < %s)" % (ext, BDT1), "Inverted-FakeB2": "%s (BDT < %s)" % (ext, BDT2), "Inverted-FakeB3": "%s (BDT < %s)" % (ext, BDT3), }) # Get histogram keyword arguments kwargs_ = GetHistoKwargs(hBaseline_Inclusive, ext, opts) # Draw the histograms plots.drawPlot(p, hBaseline_Inclusive, **kwargs_) #iro # Save plot in all formats saveName = hBaseline_Inclusive.split("/")[-1] saveName = saveName.replace("Baseline_", "") saveName = saveName.replace("Inverted_", "") saveName = saveName.replace("_AfterAllSelections", "_" + ext) saveName = saveName.replace("_AfterCRSelections", "_" + ext) savePath = os.path.join(opts.saveDir, opts.optMode) SavePlot(p, saveName, savePath, saveFormats=[".png", ".pdf"]) return
def main(hName, opts): # Setup the style style = tdrstyle.TDRStyle() # Set ROOT batch mode boolean ROOT.gROOT.SetBatch(opts.batchMode) # Setup & configure the dataset manager datasetsMgr = GetDatasetsFromDir(opts.mcrab, opts, **kwargs) datasetsMgr.updateNAllEventsToPUWeighted() datasetsMgr.PrintCrossSections() datasetsMgr.PrintLuminosities() # Set/Overwrite cross-sections for d in datasetsMgr.getAllDatasets(): if "ChargedHiggs" in d.getName(): datasetsMgr.getDataset(d.getName()).setCrossSection(1.0) # Merge datasets: All JetHT to "Data", QCD_Pt to "QCD", QCD_bEnriched to "QCD_b", single-top to "SingleTop", WW, WZ, ZZ to "Diboson" plots.mergeRenameReorderForDataMC(datasetsMgr) # Remove datasets # datasetsMgr.remove("QCD-b") # datasetsMgr.remove("QCD") # Print dataset information datasetsMgr.PrintInfo() # Create data-MC comparison plot, with the default p = plots.DataMCPlot(datasetsMgr, hName) # Create a comparison plot ratioOpts = {"ymin": 0.0, "ymax": 2.0} if kwargs.get("logY") == True: canvOpts = {"xmin": 0.0, "ymin": 1e-1, "ymaxfactor": 10} else: canvOpts = {"ymin": 0.0, "ymaxfactor": 1.2} # Draw a customised plot & Save it plots.drawPlot( p, "Plots/" + hName.replace("/", "_").replace(" ", "_").replace( "(", "_").replace(")", ""), xlabel=kwargs.get("xlabel"), ylabel=kwargs.get("ylabel"), rebinX=kwargs.get("rebinX"), rebinY=kwargs.get("rebinY"), xlabelsize=kwargs.get("xlabelsize"), ratio=kwargs.get("ratio"), stackMCHistograms=kwargs.get("stackMCHistograms"), ratioYlabel=kwargs.get("ratioYlabel"), ratioInvert=kwargs.get("ratioInvert"), addMCUncertainty=kwargs.get("addMCUncertainty"), addLuminosityText=kwargs.get("addLuminosityText"), addCmsText=kwargs.get("addCmsText"), opts=canvOpts, opts2=ratioOpts, log=kwargs.get("logY"), errorBarsX=kwargs.get("errorBarsX"), cmsExtraText=kwargs.get("cmsExtraText"), moveLegend=kwargs.get("moveLegend"), #cutLine=kwargs.get("cutValue"), cutBox={ "cutValue": kwargs.get("cutValue"), "fillColor": kwargs.get("cutFillColour"), "box": kwargs.get("cutBox"), "line": kwargs.get("cutLine"), "lessThan": kwargs.get("cutLessthan") }, ) # Remove legend? if kwargs.get("removeLegend"): p.removeLegend() # Additional text # histograms.addText(0.4, 0.9, "Alexandros Attikis", 17) # histograms.addText(0.4, 0.11, "Runs " + datasetsMgr.loadRunRange(), 17) if not opts.batchMode: raw_input("=== plotCounters.py:\n\tPress any key to quit ROOT ...") return
def PlotHistograms(datasetsMgr, histoName): # Get Histogram name and its kwargs saveName = histoName.rsplit("/")[-1] # histoName.replace("/", "_") kwargs_ = GetHistoKwargs(saveName, opts) # Create the plotting object if "Data" in datasetsMgr.getAllDatasetNames(): p = plots.DataMCPlot(datasetsMgr, histoName, saveFormats=[]) else: if opts.normalizeToLumi: p = plots.MCPlot(datasetsMgr, histoName, normalizeToLumi=opts.intLumi, saveFormats=[]) elif opts.normalizeByCrossSection: p = plots.MCPlot(datasetsMgr, histoName, normalizeByCrossSection=True, saveFormats=[], **{}) elif opts.normalizeToOne: p = plots.MCPlot(datasetsMgr, histoName, normalizeToOne=True, saveFormats=[], **{}) else: raise Exception( "One of the options --normalizeToOne, --normalizeByCrossSection, --normalizeToLumi must be enabled (set to \"True\")." ) # Overwite signal style? style = [200, 500, 800, 1000, 2000, 3000, 5000] lstyle = [ ROOT.kSolid, ROOT.kDashed, ROOT.kDashDotted, ROOT.kDotted, ROOT.kDotted, ROOT.kSolid ] for i, d in enumerate(datasetsMgr.getAllDatasets(), 0): p.histoMgr.forHisto(d.getName(), styles.getSignalStyleHToTB_M(style[i])) if 1: p.histoMgr.forEachHisto( lambda h: h.getRootHisto().SetLineStyle(ROOT.kSolid)) p.histoMgr.setHistoLegendLabelMany({ #"ChargedHiggs_HplusTB_HplusToTB_M_500_MVA0p30": "H^{+} m_{H^{+}} = 500 GeV (BDT #geq 0.3)", "ChargedHiggs_HplusTB_HplusToTB_M_%s_MVA0p30" % (opts.signalMass): "m_{H^{+}}=%s GeV (BDT #geq 0.3)" % (opts.signalMass), "ChargedHiggs_HplusTB_HplusToTB_M_%s_MVA0p40" % (opts.signalMass): "m_{H^{+}}=%s GeV (BDT #geq 0.4)" % (opts.signalMass), "ChargedHiggs_HplusTB_HplusToTB_M_%s_MVA0p50" % (opts.signalMass): "m_{H^{+}}=%s GeV (BDT #geq 0.5)" % (opts.signalMass), "ChargedHiggs_HplusTB_HplusToTB_M_%s_MVA0p60" % (opts.signalMass): "m_{H^{+}}=%s GeV (BDT #geq 0.6)" % (opts.signalMass), "ChargedHiggs_HplusTB_HplusToTB_M_%s_MVA0p70" % (opts.signalMass): "m_{H^{+}}=%s GeV (BDT #geq 0.7)" % (opts.signalMass), }) # Apply blinding of signal region if "blindingRangeString" in kwargs_: startBlind = float(kwargs_["blindingRangeString"].split("-")[1]) endBlind = float(kwargs_["blindingRangeString"].split("-")[0]) plots.partiallyBlind(p, maxShownValue=startBlind, minShownValue=endBlind, invert=True, moveBlindedText=kwargs_["moveBlindedText"]) # Draw and save the plot saveName += "_M%s" % (opts.signalMass) plots.drawPlot(p, saveName, **kwargs_) #the "**" unpacks the kwargs_ dictionary # Save the plots in custom list of saveFormats SavePlot(p, saveName, os.path.join(opts.saveDir, opts.optMode, opts.folder), [".png", ".pdf"]) return
def DoPlots(datasetsMgr, histoName, analysisType="Inverted", bType="GenuineB"): # Sanity checks IsBaselineOrInverted(analysisType) IsGenuineOrFake(bType) # Definitions defaultFolder = "" if "FakeBPurity" in histoName: defaultFolder = "FakeBPurity" elif "ForFakeBMeasurement" + histoName: defaultFolder = "ForFakeBMeasurement" else: raise Exception("This should never happen") # Define folders for inclusive/genuine/fakes inclusiveFolder = defaultFolder genuineFolder = defaultFolder + "EWKGenuineB" fakeFolder = defaultFolder + "EWKFakeB" inclusiveHisto = histoName.replace(defaultFolder, inclusiveFolder) genuineHisto = histoName.replace(defaultFolder, genuineFolder) fakeHisto = histoName.replace(defaultFolder, fakeFolder) # Get the inclusive histograms p0 = plots.DataMCPlot(datasetsMgr, inclusiveHisto) Data = p0.histoMgr.getHisto("Data").getRootHisto().Clone("Data") # Get the genuine-b histograms p1 = plots.DataMCPlot(datasetsMgr, genuineHisto) EWKGenuineB = p1.histoMgr.getHisto("EWK").getRootHisto().Clone( "EWKGenuineB") QCDGenuineB = p1.histoMgr.getHisto("QCD").getRootHisto().Clone( "QCDGenuineB") # Get the fake-b histograms p2 = plots.DataMCPlot(datasetsMgr, fakeHisto) EWKFakeB = p2.histoMgr.getHisto("EWK").getRootHisto().Clone("EWKFakeB") QCDFakeB = p2.histoMgr.getHisto("QCD").getRootHisto().Clone("QCDFakeB") # Normalize histograms to unit area if 0: Data.Scale(1.0 / Data.Integral()) EWKGenuineB.Scale(1.0 / EWKGenuineB.Integral()) EWKFakeB.Scale(1.0 / EWKFakeB.Integral()) QCDGenuineB.Scale(1.0 / QCDGenuineB.Integral()) QCDFakeB.Scale(1.0 / EWKFakeB.Integral()) # Create the final plot object comparisonList = [EWKGenuineB, QCDGenuineB, EWKFakeB, QCDFakeB] p = plots.ComparisonManyPlot(Data, comparisonList, saveFormats=[]) p.setLuminosity(GetLumi(datasetsMgr)) # Apply styles p.histoMgr.forHisto("Data", styles.getDataStyle()) p.histoMgr.forHisto("EWKGenuineB", styles.getAltEWKStyle()) #GenuineBStyle() p.histoMgr.forHisto("QCDGenuineB", styles.getQCDStyle()) p.histoMgr.forHisto("EWKFakeB", styles.getGenuineBStyle()) p.histoMgr.forHisto("QCDFakeB", styles.getFakeBStyle()) # Set draw style p.histoMgr.setHistoDrawStyle("Data", "AP") p.histoMgr.setHistoDrawStyle("EWKGenuineB", "AP") p.histoMgr.setHistoDrawStyle("QCDGenuineB", "AP") p.histoMgr.setHistoDrawStyle("EWKFakeB", "AP") p.histoMgr.setHistoDrawStyle("QCDFakeB", "AP") # Set legend style p.histoMgr.setHistoLegendStyle("Data", "P") p.histoMgr.setHistoLegendStyle("EWKGenuineB", "P") p.histoMgr.setHistoLegendStyle("QCDGenuineB", "P") p.histoMgr.setHistoLegendStyle("EWKFakeB", "P") p.histoMgr.setHistoLegendStyle("QCDFakeB", "P") # p.histoMgr.setHistoLegendStyleAll("LP") # Set legend labels p.histoMgr.setHistoLegendLabelMany({ "Data": "Data", "EWKGenuineB": "EWK-GenuineB", "QCDGenuineB": "QCD-GenuineB", "EWKFakeB": "EWK-FakeB", "QCDFakeB": "QCD-FakeB", #"Data" : "Data (%s)" % (analysisType), #"EWKGenuineB": "EWK-GenuineB (%s)" % (analysisType), #"QCDGenuineB": "QCD-GenuineB (%s)" % (analysisType), #"EWKFakeB" : "EWK-FakeB (%s)" % (analysisType), #"QCDFakeB" : "QCD-FakeB (%s)" % (analysisType), }) # Draw the histograms _cutBox = None _rebinX = 1 _opts = {"ymin": 1e0, "ymaxfactor": 2.0} _format = "%0.0f" _xlabel = None if "dijetm" in histoName.lower(): _rebinX = 2 _units = "GeV/c^{2}" _format = "%0.0f " + _units _xlabel = "m_{jj} (%s)" % (_units) _cutBox = { "cutValue": 80.399, "fillColor": 16, "box": False, "line": True, "greaterThan": True } _opts["xmax"] = 400.0 if "trijetm" in histoName.lower(): _rebinX = 5 _units = "GeV/c^{2}" _format = "%0.0f " + _units _xlabel = "m_{jjb} (%s)" % _units _cutBox = { "cutValue": 173.21, "fillColor": 16, "box": False, "line": True, "greaterThan": True } _opts["xmax"] = 1500.0 if "pt" in histoName.lower(): _rebinX = 2 _format = "%0.0f GeV/c" if "eta" in histoName.lower(): _format = "%0.2f" _cutBox = { "cutValue": 0., "fillColor": 16, "box": False, "line": True, "greaterThan": True } _opts["xmin"] = -3.0 _opts["xmax"] = +3.0 if "deltaeta" in histoName.lower(): _format = "%0.2f" _opts["xmin"] = 0.0 _opts["xmax"] = 6.0 if "bdisc" in histoName.lower(): _format = "%0.2f" if "tetrajetm" in histoName.lower(): _rebinX = 10 _units = "GeV/c^{2}" _format = "%0.0f " + _units _xlabel = "m_{jjjb} (%s)" % (_units) _opts["xmax"] = 3500.0 if "ancestry" in histoName.lower(): _rebinX = 1 _units = "" _format = "%0.0f " + _units _opts["xmax"] = 32.0 plots.drawPlot( p, histoName, xlabel=_xlabel, ylabel="Arbitrary Units / %s" % (_format), log=True, rebinX=_rebinX, cmsExtraText="Preliminary", createLegend={ "x1": 0.62, "y1": 0.72, "x2": 0.92, "y2": 0.92 }, opts=_opts, opts2={ "ymin": 0.0, "ymax": 1.5 }, #{"ymin": 0.6, "ymax": 1.4}, ratio=True, ratioInvert=False, ratioYlabel="Ratio", cutBox=_cutBox, ) # Save plot in all formats SavePlot(p, histoName, os.path.join(opts.saveDir, "GenuineVsFake", opts.optMode)) return
def main(argv): dirs = [] if len(sys.argv) < 2: usage() dirs.append(sys.argv[1]) dirs_signal = ["../../SignalAnalysis_140605_143702/"] QCDInvertedNormalization = sort( QCDInvertedNormalizationFactors.QCDInvertedNormalization) labels, QCDInvertedNormalizationFilteredEWKFakeTaus = getSortedLabelsAndFactors( QCDInvertedNormalizationFactorsFilteredEWKFakeTaus. QCDInvertedNormalization) analysis_inverted = "signalAnalysisInvertedTau" analysis = "signalAnalysis" optModes = [] #optModes.append("OptQCDTailKillerZeroPlus") optModes.append("OptQCDTailKillerLoosePlus") optModes.append("OptQCDTailKillerMediumPlus") optModes.append("OptQCDTailKillerTightPlus") varHistoName = "shapeEWKGenuineTausTransverseMass" nomHistoName = "shapeTransverseMass" signalHistoName = "shapeEWKFakeTausTransverseMass" #Optimal: 0.8, 0.82, 0.9 ###w_list = [0.65, 0.7, 0.76] #old baseline ft w_list = [0.66, 0.67, 0.75] #w_list = [0.4, 0.45, 0.5, 0.55, 0.6, 0.65, 0.7, 0.75, 0.8, 0.85, 0.9, 1] #defaultBinning = systematics.getBinningForPlot("shapeTransverseMass") defaultBinning = [0, 20, 40, 60, 80, 100, 120, 140, 160, 200, 400] defaultBinning_array = array.array("d", defaultBinning) diff_opt = [] for optMode in optModes: diff_list = [] for w in w_list: var_values = [] nom_values = [] # baseline fake taus mt_baseline_faketaus_data = getDataSets(dirs_signal, dataEra, searchMode, analysis, optMode) mtplot_signalfaketaus = plots.DataMCPlot(mt_baseline_faketaus_data, signalHistoName) mt_signalfaketaus = mtplot_signalfaketaus.histoMgr.getHisto( "EWK").getRootHisto().Clone(signalHistoName) # inverted fake taus mt_inverted_faketaus_data = getDataSets(dirs, dataEra, searchMode, analysis_inverted, optMode) histonames_var = mt_inverted_faketaus_data.getDataset( "Data").getDirectoryContent(varHistoName) histonames_nom = mt_inverted_faketaus_data.getDataset( "Data").getDirectoryContent(nomHistoName) bins_var = getBins(histonames_var, varHistoName) bins_nom = getBins(histonames_nom, nomHistoName) normalization_var_qg = getNormalization( bins_var, w, QCDInvertedNormalizationFilteredEWKFakeTaus, True, True) normalization_var = getNormalization( bins_var, w, QCDInvertedNormalizationFilteredEWKFakeTaus, True, False) normalization_nom = getNormalization(bins_nom, w, QCDInvertedNormalization, False, False) mt_var_qg = getMt(mt_inverted_faketaus_data, bins_var, varHistoName, normalization_var_qg) mt_var = getMt(mt_inverted_faketaus_data, bins_var, varHistoName, normalization_var) mt_nom = getMt(mt_inverted_faketaus_data, bins_nom, nomHistoName, normalization_nom) mt_nom.Add(mt_signalfaketaus) mt_var_qg.SetName( "QCD(Data)+EWK+t#bar{t}(Data, mis-ID. #tau), q-g bal.") mt_var.SetName("QCD(Data)+EWK+t#bar{t}(Data, mis-ID. #tau)") mt_nom.SetName("QCD(Data)+EWK+t#bar{t}(MC, mis-ID. #tau)") mt_var_qg.SetLineWidth(4) mt_var.SetLineColor(14) mt_nom.SetLineColor(2) mt_var_qg = mt_var_qg.Rebin( len(defaultBinning) - 1, "", defaultBinning_array) mt_var = mt_var.Rebin( len(defaultBinning) - 1, "", defaultBinning_array) mt_nom = mt_nom.Rebin( len(defaultBinning) - 1, "", defaultBinning_array) for i in range(0, mt_nom.GetSize()): var_values.append(mt_var_qg.GetBinContent(i)) nom_values.append(mt_nom.GetBinContent(i)) style = tdrstyle.TDRStyle() varPlots = [mt_var, mt_var_qg] plot = plots.ComparisonManyPlot(mt_nom, varPlots) plot.createFrame(optMode.replace( "Opt", "Mt_DataDrivenVsMC_" + "w=" + str(w) + "_"), createRatio=True) moveLegend = {"dx": -0.35, "dy": 0.05} plot.setLegend( histograms.moveLegend(histograms.createLegend(), **moveLegend)) histograms.addText( 0.65, 0.3, optMode.replace("OptQCDTailKiller", "R_{BB} ").replace("Plus", ""), 25) histograms.addCmsPreliminaryText() histograms.addEnergyText() lumi = mt_inverted_faketaus_data.getDataset("Data").getLuminosity() histograms.addLuminosityText(x=None, y=None, lumi=lumi) plot.draw() plot.save() mt_var_qg.Delete() mt_var.Delete() mt_nom.Delete() #TFile.CurrentFile().Close("R") mt_baseline_faketaus_data.close() mt_inverted_faketaus_data.close() ROOT.gROOT.CloseFiles() ROOT.gROOT.GetListOfCanvases().Delete() ROOT.gDirectory.GetList().Delete() #print var_values #print nom_values # difference metrics num = 0 denom = 0 for i in range(0, len(nom_values)): num += var_values[i] * (var_values[i] - nom_values[i])**2 denom += var_values[i] diff = num / denom diff_list.append(diff) diff_opt.append(diff_list) os.system("rm MtOptimal/*") os.system("mkdir -p MtOptimal") print "\nWeights:\t", w_list, '\n' optimalWeights = {} for i in range(0, len(diff_opt)): print optModes[i] print "Differences:\t", diff_opt[i], "- Optimal: w =", w_list[ diff_opt[i].index(min(diff_opt[i]))] optimalWeights[optModes[i]] = w_list[diff_opt[i].index(min( diff_opt[i]))] command = "cp *" + str(w_list[diff_opt[i].index(min( diff_opt[i]))]) + "*" + optModes[i].replace("Opt", "") + ".eps MtOptimal" os.system(command) print optimalWeights writeWeightsToFile("OptimalWeights.py", optimalWeights) writeNormalizationToFile("QCDPlusEWKFakeTauNormalizationFactors.py", normalization_var_qg, labels)
def DataMCPlot(datasetsMgr, json): Verbose("Creating Data-MC plot") ##ATHER # evtCount = counter.EventCounter(datasetsMgr) # evtCount.normalizeToOne() # Print dataset information # datasetsMgr.PrintInfo() # #ATHER # Create the Data-MC Plot p = plots.DataMCPlot(datasetsMgr, json["histogram"]) # Label size (optional. Commonly Used in counters) xlabelSize = None if "xlabelsize" in json: xlabelSize = json["xlabelsize"] ylabelSize = None if "ylabelsize" in json: ylabelSize = json["ylabelsize"] # Draw a customised plot saveName = os.path.join(json["saveDir"], json["title"]) plots.drawPlot( p, saveName, xlabel=json["xlabel"], ylabel=json["ylabel"], rebinX=json["rebinX"], rebinY=json["rebinY"], ratioYlabel=json["ratioYlabel"], ratio=json["ratio"] == "True", stackMCHistograms=json["stackMCHistograms"] == "True", ratioInvert=json["ratioInvert"] == "True", addMCUncertainty=json["addMCUncertainty"] == "True", addLuminosityText=json["addLuminosityText"] == "True", addCmsText=json["addCmsText"] == "True", cmsExtraText=json["cmsExtraText"], opts=json["opts"], opts2=json["ratioOpts"], log=json["logY"] == "True", errorBarsX=json["errorBarsX"] == "True", moveLegend=json["moveLegend"], # cutLine = json["cutValue"], #cannot have this and "cutBox" defined cutBox={ "cutValue": json["cutValue"], "fillColor": json["cutFillColour"], "box": json["cutBox"] == "True", "line": json["cutLine"] == "True", "greaterThan": json["cutGreaterThan"] == "True" }, xlabelsize=xlabelSize, ylabelsize=ylabelSize, ) # Remove legend? if json["removeLegend"] == "True": p.removeLegend() # Additional text histograms.addText(json["extraText"].get("x"), json["extraText"].get("y"), json["extraText"].get("text"), json["extraText"].get("size")) # Save in all formats chosen by user saveFormats = json["saveFormats"] for i, ext in enumerate(saveFormats): Print("%s" % saveName + ext, i == 0) p.saveAs(saveName, formats=saveFormats) return
def main(argv): dirs = [] if len(sys.argv) < 2: usage() dirs.append(sys.argv[1]) QCDInvertedNormalization = QCDInvertedNormalizationFactors.QCDInvertedNormalization QCDInvertedNormalizationFilteredEWKFakeTaus = QCDInvertedNormalizationFactorsFilteredEWKFakeTaus.QCDInvertedNormalization analysis = "signalAnalysisInvertedTau" optModes = [] #optModes.append("OptQCDTailKillerZeroPlus") optModes.append("OptQCDTailKillerLoosePlus") optModes.append("OptQCDTailKillerMediumPlus") optModes.append("OptQCDTailKillerTightPlus") #optModes.append("OptQCDTailKillerVeryTightPlus") #optModes.append("OnlyGenuineMCTausFalse") #optModes.append("OnlyGenuineMCTausTrue") #Optimal: 0.8, 0.82, 0.9 #w1_list = [0.8, 0.82, 0.84, 0.87] #w1_list = [0.8, 0.82, 0.9, 1] w1_list = [0.9] defaultBinning = systematics.getBinningForPlot("shapeTransverseMass") diff_opt = [] for optMode in optModes: diff_list = [] for w1 in w1_list: var_values = [] nom_values = [] w2 = 1 - w1 color = 1 #signal dirs_signal = ["../../SignalAnalysis_140605_143702/"] datasets_signal = dataset.getDatasetsFromMulticrabDirs( dirs_signal, dataEra=dataEra, searchMode=searchMode, analysisName=analysis.replace("InvertedTau", ""), optimizationMode=optMode) datasets_signal.updateNAllEventsToPUWeighted() datasets_signal.loadLuminosities() datasets_signal.remove( filter(lambda name: "TTToHplus" in name, datasets_signal.getAllDatasetNames())) datasets_signal.remove( filter(lambda name: "HplusTB" in name, datasets_signal.getAllDatasetNames())) datasets_signal.remove( filter(lambda name: "Hplus_taunu_t-channel" in name, datasets_signal.getAllDatasetNames())) datasets_signal.remove( filter(lambda name: "Hplus_taunu_tW-channel" in name, datasets_signal.getAllDatasetNames())) datasets_signal.remove( filter(lambda name: "TTJets_SemiLept" in name, datasets_signal.getAllDatasetNames())) datasets_signal.remove( filter(lambda name: "TTJets_FullLept" in name, datasets_signal.getAllDatasetNames())) datasets_signal.remove( filter(lambda name: "TTJets_Hadronic" in name, datasets_signal.getAllDatasetNames())) plots.mergeRenameReorderForDataMC(datasets_signal) datasets_signal.merge( "EWK", ["TTJets", "WJets", "DYJetsToLL", "SingleTop", "Diboson"]) mtplot_signalfaketaus = plots.DataMCPlot( datasets_signal, "shapeEWKFakeTausTransverseMass") mt_signalfaketaus = mtplot_signalfaketaus.histoMgr.getHisto( "EWK").getRootHisto().Clone("shapeEWKFakeTausTransverseMass") mt_signalfaketaus.SetName("BaselineFakeTaus") myBinning = [0, 20, 40, 60, 80, 100, 120, 140, 160, 200, 400] myArray = array.array("d", myBinning) fitBinning = [] for i in range(0, 45): fitBinning.append(i * 10) fitArray = array.array("d", fitBinning) mt_baseline = mt_signalfaketaus #rangeMin = mt_signalfaketaus.GetXaxis().GetXmin() #rangeMax = mt_signalfaketaus.GetXaxis().GetXmax() #theFit = TF1('theFit',FitFunction(),rangeMin,rangeMax,4) #theFit.SetParLimits(0,0.5,10000) #theFit.SetParLimits(1,90,10000) #theFit.SetParLimits(2,30,10000) #theFit.SetParLimits(3,0.001,10000) #mt_signalfaketaus.Fit(theFit,"R") #theFit.SetRange(mt_signalfaketaus.GetXaxis().GetXmin(),mt_signalfaketaus.GetXaxis().GetXmax()) #theFit.SetLineStyle(2) #theFit.SetLineColor(4) #theFit.SetLineWidth(3) #theFit.Draw() #mt_corr = theFit.GetHistogram() #mt_corr = mt_corr.Rebin(len(fitBinning)-1,"",fitArray) #mt_corr.Scale(mt_baseline.GetMaximum()/mt_corr.GetMaximum()) for HISTONAME in histoNameList: var = False if HISTONAME == "shapeEWKGenuineTausTransverseMass": var = True datasets = dataset.getDatasetsFromMulticrabDirs( dirs, dataEra=dataEra, searchMode=searchMode, analysisName=analysis, optimizationMode=optMode) datasets.updateNAllEventsToPUWeighted() datasets.loadLuminosities() plots.mergeRenameReorderForDataMC(datasets) datasets.merge( "EWK", ["TTJets", "WJets", "DYJetsToLL", "SingleTop", "Diboson"]) histonames = datasets.getDataset("Data").getDirectoryContent( HISTONAME) bins = [] for histoname in histonames: binname = histoname.replace(HISTONAME, "") if not binname == "Inclusive": bins.append(binname) for i, bin in enumerate(bins): mtplot = plots.DataMCPlot( datasets, HISTONAME + "/" + HISTONAME + bin) if i == 0: mt = mtplot.histoMgr.getHisto( "Data").getRootHisto().Clone(HISTONAME + "/" + HISTONAME + bin) mt_ewk = mtplot.histoMgr.getHisto( "EWK").getRootHisto().Clone(HISTONAME + "/" + HISTONAME + bin) mtn = mtplot.histoMgr.getHisto( "Data").getRootHisto().Clone(HISTONAME + "/" + HISTONAME + bin) mtn_ewk = mtplot.histoMgr.getHisto( "EWK").getRootHisto().Clone(HISTONAME + "/" + HISTONAME + bin) if var: legendName = "QCD(Data)+EWK+t#bar{t}(Data, mis-ID. #tau)" else: legendName = "QCD(Data)+EWK+t#bar{t}(MC, mis-ID. #tau)" legendName = legendName.replace("Plus", "") mt.SetName(legendName) mt.SetLineColor(color) mt.Add(mt_ewk, -1) mtn.Add(mtn_ewk, -1) mtn.Scale(QCDInvertedNormalization[str(i)]) if var: scale = w1 * QCDInvertedNormalizationFilteredEWKFakeTaus[ str( i )] + w2 * QCDInvertedNormalizationFilteredEWKFakeTaus[ str(i) + "EWK_FakeTaus"] mt.Scale(scale) else: mt.Scale(QCDInvertedNormalization[str(i)]) color += 1 if color == 5: color += 1 else: h = mtplot.histoMgr.getHisto( "Data").getRootHisto().Clone(HISTONAME + "/" + HISTONAME + bin) mt_ewk = mtplot.histoMgr.getHisto( "EWK").getRootHisto().Clone(HISTONAME + "/" + HISTONAME + bin) hn = mtplot.histoMgr.getHisto( "Data").getRootHisto().Clone(HISTONAME + "/" + HISTONAME + bin) mtn_ewk = mtplot.histoMgr.getHisto( "EWK").getRootHisto().Clone(HISTONAME + "/" + HISTONAME + bin) h.Add(mt_ewk, -1) hn.Add(mtn_ewk, -1) hn.Scale(QCDInvertedNormalization[str(i)]) if var: scale = w1 * QCDInvertedNormalizationFilteredEWKFakeTaus[ str( i )] + w2 * QCDInvertedNormalizationFilteredEWKFakeTaus[ str(i) + "EWK_FakeTaus"] h.Scale(scale) else: h.Scale(QCDInvertedNormalization[str(i)]) mt.Add(h) mtn.Add(hn) #mt = mt.Rebin(len(myBinning)-1,"",myArray) #mt_corr = mt_corr.Rebin(len(myBinning)-1,"",myArray) if not var: mt.Add(mt_baseline) #mt.Add(mt_corr) #myBinning = [] #for i in range(0,11): # myBinning.append(20*i) #myBinning.append(400) #myArray = array.array("d",defaultBinning) mt = mt.Rebin(len(myBinning) - 1, "", myArray) for i in range(0, mt.GetSize()): if var: var_values.append(mt.GetBinContent(i)) else: nom_values.append(mt.GetBinContent(i)) if var: #mt.SetLineStyle(2) var_hist = mt else: #mt.SetLineStyle(2) nom_hist = mt style = tdrstyle.TDRStyle() #gStyle.SetOptStat(1101) #mt_data.SetStats(1) #gPad.Update() bins = [0, 390, 400] arr = array.array("d", bins) mtn = mtn.Rebin(len(bins) - 1, "", arr) plot_data = plots.PlotBase() plot_data.histoMgr.appendHisto(histograms.Histo(mtn, "Data")) plot_data.createFrame("Data_" + HISTONAME + "_" + optMode + "_" + str(w1)) plot_data.draw() plot_data.save() plot = plots.ComparisonPlot(nom_hist, var_hist) plot.createFrame(optMode.replace( "Opt", "Mt_" + "w1=" + str(w1) + "_w2=" + str(w2) + "_DataDrivenVsMC_"), createRatio=True) moveLegend = {"dx": -0.295, "dy": 0.05} plot.setLegend( histograms.moveLegend(histograms.createLegend(), **moveLegend)) histograms.addText( 0.65, 0.20, optMode.replace("OptQCDTailKiller", "R_{BB} ").replace("Plus", ""), 25) histograms.addCmsPreliminaryText() histograms.addEnergyText() lumi = datasets.getDataset("Data").getLuminosity() histograms.addLuminosityText(x=None, y=None, lumi=lumi) plot.draw() plot.save() num = 0 denom = 0 #print var_values for i in range(0, len(nom_values)): num += var_values[i] * (var_values[i] - nom_values[i])**2 denom += var_values[i] diff = num / denom diff_list.append(diff) diff_opt.append(diff_list) print w1_list, '\n' for i in range(0, len(diff_opt)): print diff_opt[i] print w1_list[diff_opt[i].index(min(diff_opt[i]))] mt_baseline = mt_baseline.Rebin(len(bins) - 1, "", arr) plot_bft = plots.PlotBase() plot_bft.histoMgr.appendHisto(histograms.Histo(mt_baseline, "baseline")) #mt_corr.Scale(2) #plot_bft.histoMgr.appendHisto(histograms.Histo(mt_corr,"test")) #rangeMin = mt_signalfaketaus.GetXaxis().GetXmin() #rangeMax = mt_signalfaketaus.GetXaxis().GetXmax() #theFit = TF1('theFit',FitFunction(),rangeMin,rangeMax,4) #theFit.SetParLimits(0,0.5,10000) #theFit.SetParLimits(1,90,10000) #theFit.SetParLimits(2,30,10000) #theFit.SetParLimits(3,0.001,10000) #mt_signalfaketaus.Fit(theFit,"R") #theFit.SetRange(mt_signalfaketaus.GetXaxis().GetXmin(),mt_signalfaketaus.GetXaxis().GetXmax()) #theFit.SetLineStyle(2) #theFit.SetLineColor(4) #theFit.SetLineWidth(3) #theFit.Draw() #mt_corr = theFit.GetHistogram() #mt_corr = mt_corr.Rebin(len(fitBinning)-1,"",fitArray) #mt_corr.Scale(mt_baseline.GetMaximum()/mt_corr.GetMaximum()) #plot_bft.histoMgr.appendHisto(histograms.Histo(mt_corr,"test")) #plot_bft.histoMgr.appendHisto(histograms.Histo(theFit,"theFit")) plot_bft.createFrame('BaselineFakeTaus') plot_bft.draw() plot_bft.save()
def main(argv, dsetMgr, moduleInfoString): COMBINEDHISTODIR = "ForQCDNormalization" FAKEHISTODIR = "ForQCDNormalizationEWKFakeTaus" GENUINEHISTODIR = "ForQCDNormalizationEWKGenuineTaus" comparisonList = ["AfterStdSelections"] dirs = [] dirs.append(sys.argv[1]) # Check multicrab consistency # consistencyCheck.checkConsistencyStandalone(dirs[0],dsetMgr,name="QCD inverted") #FIXME needs to be updated # As we use weighted counters for MC normalisation, we have to # update the all event count to a separately defined value because # the analysis job uses skimmed pattuple as an input dsetMgr.updateNAllEventsToPUWeighted() # Read integrated luminosities of data dsetMgr from lumi.json dsetMgr.loadLuminosities() if verbose: print "Datasets list (initial):" print dsetMgr.getMCDatasetNames() # Include only 120 mass bin of HW and HH dsetMgr dsetMgr.remove( filter(lambda name: "TTToHplus" in name and not "M120" in name, dsetMgr.getAllDatasetNames())) dsetMgr.remove( filter(lambda name: "HplusTB" in name, dsetMgr.getAllDatasetNames())) dsetMgr.remove( filter(lambda name: "DY2JetsToLL" in name, dsetMgr.getAllDatasetNames())) dsetMgr.remove( filter(lambda name: "DY3JetsToLL" in name, dsetMgr.getAllDatasetNames())) dsetMgr.remove( filter(lambda name: "DY4JetsToLL" in name, dsetMgr.getAllDatasetNames())) # Ignore DY dataset with HERWIG hadronization (it's only for testing) dsetMgr.remove(filter(lambda name: "DYJetsToLL_M_50_HERWIGPP" in name, dsetMgr.getAllDatasetNames()), close=False) if verbose: print "Datasets after filter removals:" print dsetMgr.getMCDatasetNames() # Default merging nad ordering of data and MC dsetMgr # All data dsetMgr to "Data" # All QCD dsetMgr to "QCD" # All single top dsetMgr to "SingleTop" # WW, WZ, ZZ to "Diboson" plots.mergeRenameReorderForDataMC(dsetMgr) if verbose: print "Datasets after mergeRenameReorderForDataMC:" print dsetMgr.getMCDatasetNames() # Only WJets/WJetsToLNu or WJetsToLNu_HT_* should be used (not both) if useWJetsHT: dsetMgr.remove(filter(lambda name: "WJets" == name, dsetMgr.getAllDatasetNames()), close=False) else: dsetMgr.remove(filter(lambda name: "WJetsHT" in name, dsetMgr.getAllDatasetNames()), close=False) print "Datasets used for EWK (after choosing between WJets or WJetsHT sample):" print dsetMgr.getMCDatasetNames() # Set BR(t->H) to 0.05, keep BR(H->tau) in 1 xsect.setHplusCrossSectionsToBR(dsetMgr, br_tH=0.05, br_Htaunu=1) # Merge WH and HH dsetMgr to one (for each mass bin) plots.mergeWHandHH(dsetMgr) # Merge MC EWK samples as one EWK sample myMergeList = [] # Always use TT (or TTJets) as a part of the EWK background if "TT" in dsetMgr.getMCDatasetNames(): myMergeList.append("TT") # Powheg, no neg. weights -> large stats. else: myMergeList.append("TTJets") # Madgraph with negative weights print "Warning: using TTJets as input, but this is suboptimal. Please switch to the TT sample (much more stats.)." # Always use WJets as a part of the EWK background if useWJetsHT: myMergeList.append("WJetsHT") else: myMergeList.append("WJets") # For SY, single top and diboson, use only if available: if "DYJetsToQQHT" in dsetMgr.getMCDatasetNames(): myMergeList.append("DYJetsToQQHT") if "DYJetsToLL" in dsetMgr.getMCDatasetNames(): myMergeList.append("DYJetsToLL") else: print "Warning: ignoring DYJetsToLL sample (since merged sample does not exist) ..." if "SingleTop" in dsetMgr.getMCDatasetNames(): myMergeList.append("SingleTop") else: print "Warning: ignoring single top sample (since merged sample does not exist) ..." if "Diboson" in dsetMgr.getMCDatasetNames(): myMergeList.append("Diboson") else: print "Warning: ignoring diboson sample (since merged sample does not exist) ..." for item in myMergeList: if not item in dsetMgr.getMCDatasetNames(): raise Exception( "Error: tried to use dataset '%s' as part of the merged EWK dataset, but the dataset '%s' does not exist!" % (item, item)) dsetMgr.merge("EWK", myMergeList) if verbose: print "\nFinal merged dataset list:\n" print dsetMgr.getMCDatasetNames() # Apply TDR style style = tdrstyle.TDRStyle() style.setOptStat(True) for HISTONAME in comparisonList: BASELINETAUHISTONAME = "NormalizationMETBaselineTau" + HISTONAME + "/NormalizationMETBaselineTau" + HISTONAME INVERTEDTAUHISTONAME = "NormalizationMETInvertedTau" + HISTONAME + "/NormalizationMETInvertedTau" + HISTONAME FITMIN = None FITMAX = None #===== Infer binning information and labels histonames = dsetMgr.getDataset("Data").getDirectoryContent( COMBINEDHISTODIR + "/NormalizationMETBaselineTau" + HISTONAME) bins = [] binLabels = [] if histonames == None: # Assume that only inclusive bin exists name = COMBINEDHISTODIR + "/NormalizationMETBaselineTau" + HISTONAME if not dsetMgr.getDataset("Data").hasRootHisto(name): raise Exception( "Error: Cannot find histogram or directory of name '%s'!" % name) BASELINETAUHISTONAME = "NormalizationMETBaselineTau" + HISTONAME INVERTEDTAUHISTONAME = "NormalizationMETInvertedTau" + HISTONAME bins = [""] binLabels = ["Inclusive"] else: for hname in histonames: binIndex = hname.replace( "NormalizationMETBaselineTau" + HISTONAME, "") # print "DEBUG: We are looking for hisrogram "+COMBINEDHISTODIR+"/"+BASELINETAUHISTONAME+binIndex hDummy = dsetMgr.getDataset("Data").getDatasetRootHisto( COMBINEDHISTODIR + "/" + BASELINETAUHISTONAME + binIndex).getHistogram() title = hDummy.GetTitle() title = title.replace("METBaseline" + HISTONAME, "") if hDummy.Integral() > 0.0: bins.append(binIndex) if binIndex == "Inclusive": binLabels.append(binIndex) else: binLabels.append( QCDNormalization.getModifiedBinLabelString(title)) if FITMIN == None: FITMIN = hDummy.GetXaxis().GetXmin() FITMAX = hDummy.GetXaxis().GetXmax() hDummy.Delete() else: print "Skipping bin '%s' (%s) because it has no entries" % ( binIndex, QCDNormalization.getModifiedBinLabelString(title)) print "\nHistogram bins available", bins # Select bins by filter if len(selectOnlyBins) > 0: oldBinLabels = binLabels[:] oldBins = bins[:] binLabels = [] bins = [] for k in selectOnlyBins: for i in range(len(oldBinLabels)): if k == oldBinLabels[i] or k == oldBins[i]: binLabels.append(oldBinLabels[i]) bins.append(oldBins[i]) print "Using bins ", bins print "\nBin labels" for i in range(len(binLabels)): line = bins[i] while len(line) < 10: line += " " line += ": " + binLabels[i] print line print #===== Initialize normalization calculator #manager = QCDNormalization.QCDNormalizationManagerExperimental1(binLabels) manager = QCDNormalization.QCDNormalizationManagerDefault( binLabels, dirs[0], moduleInfoString) #===== Create templates (EWK fakes, EWK genuine, QCD; data template is created by manager) template_EWKFakeTaus_Baseline = manager.createTemplate( "EWKFakeTaus_Baseline") template_EWKFakeTaus_Inverted = manager.createTemplate( "EWKFakeTaus_Inverted") template_EWKGenuineTaus_Baseline = manager.createTemplate( "EWKGenuineTaus_Baseline") template_EWKGenuineTaus_Inverted = manager.createTemplate( "EWKGenuineTaus_Inverted") template_EWKInclusive_Baseline = manager.createTemplate( "EWKInclusive_Baseline") template_EWKInclusive_Inverted = manager.createTemplate( "EWKInclusive_Inverted") template_QCD_Baseline = manager.createTemplate("QCD_Baseline") template_QCD_Inverted = manager.createTemplate("QCD_Inverted") #===== Define fit functions and fit parameters # The available functions are defined in the FitFunction class in the QCDMeasurement/python/QCDNormalization.py file # Inclusive EWK # The function is essentially pure Gaussian up to boundary value, and exponential after that, i.e. # A*Gaus(x, mean,sigma) when x > boundary_x # A*Gaus(boundary_x, mean,sigma)*exp(-beta*x) # par[0] = overall normalization A # par[1] = mean # par[3] = sigma # par[4] = beta in the exponential tail boundary = 160 template_EWKInclusive_Baseline.setFitter( QCDNormalization.FitFunction("EWKFunction", boundary=boundary, norm=1, rejectPoints=1), FITMIN, FITMAX) template_EWKInclusive_Baseline.setDefaultFitParam( defaultLowerLimit=[0.5, 90, 30, 0.0001], defaultUpperLimit=[30, 250, 60, 1.0]) # Fake tau and QCD # Note that the same function is used for QCD only and QCD+EWK fakes (=Fake Tau) # Old function, used until May 2017 # template_QCD_Inverted.setFitter(QCDNormalization.FitFunction("QCDFunction", norm=1), FITMIN, FITMAX) # template_QCD_Inverted.setDefaultFitParam(defaultLowerLimit=[ 30, 0.1, 0.1, 0, 10, 0.0, 0.0001], # defaultUpperLimit=[ 130, 20, 20, 200, 200, 1.0, 1.0]) # Latest version of the Rayleigh peak with shift + Gaussian + Exponential combination, used from March 2018, i.e. # A*((x-b)/sigma^2)*exp((x-b)^2/(2*sigma^2))+B*Gaus(x,mean,sigma2)+C*exp(-beta*x) # par[0] sigma for Rayielgh term # par[1] overall normalization A # par[2] peak shift b for Rayleigh term # par[3] normalization B for the Gaussian term # par[4] normalization C for the exponential tail # par[5] mean for Gaussian term # par[6] sigma2 for Gaussian term # par[7] beta for exponential tail template_QCD_Inverted.setFitter( QCDNormalization.FitFunction("QCDFunctionWithPeakShiftClear", norm=1), FITMIN, FITMAX) template_QCD_Inverted.setDefaultFitParam( defaultLowerLimit=[30, 0.1, -10, 0, -20, 10, 0.0001, 0.0001], defaultUpperLimit=[130, 20, 10, 20, 200, 100, 1.0, 0.05]) #===== Loop over tau pT bins for i, binStr in enumerate(bins): print "\n********************************" print "*** Fitting bin %s" % binLabels[i] print "********************************\n" #===== Reset bin results manager.resetBinResults() #===== Obtain histograms for normalization # Data histoName = COMBINEDHISTODIR + "/" + BASELINETAUHISTONAME + binStr hmetBase_data = plots.DataMCPlot( dsetMgr, histoName).histoMgr.getHisto( "Data").getRootHisto().Clone(histoName) histoName = COMBINEDHISTODIR + "/" + INVERTEDTAUHISTONAME + binStr hmetInverted_data = plots.DataMCPlot( dsetMgr, histoName).histoMgr.getHisto( "Data").getRootHisto().Clone(histoName) # EWK genuine taus histoName = GENUINEHISTODIR + "/" + BASELINETAUHISTONAME + binStr hmetBase_EWK_GenuineTaus = plots.DataMCPlot( dsetMgr, histoName).histoMgr.getHisto( "EWK").getRootHisto().Clone(histoName) histoName = GENUINEHISTODIR + "/" + INVERTEDTAUHISTONAME + binStr hmetInverted_EWK_GenuineTaus = plots.DataMCPlot( dsetMgr, histoName).histoMgr.getHisto( "EWK").getRootHisto().Clone(histoName) # EWK fake taus histoName = FAKEHISTODIR + "/" + BASELINETAUHISTONAME + binStr hmetBase_EWK_FakeTaus = plots.DataMCPlot( dsetMgr, histoName).histoMgr.getHisto( "EWK").getRootHisto().Clone(histoName) histoName = FAKEHISTODIR + "/" + INVERTEDTAUHISTONAME + binStr hmetInverted_EWK_FakeTaus = plots.DataMCPlot( dsetMgr, histoName).histoMgr.getHisto( "EWK").getRootHisto().Clone(histoName) #===== Obtain inclusive EWK histograms hmetBase_EWKinclusive = hmetBase_EWK_GenuineTaus.Clone( "EWKinclusiveBase") hmetBase_EWKinclusive.Add(hmetBase_EWK_FakeTaus, 1.0) hmetInverted_EWKinclusive = hmetInverted_EWK_GenuineTaus.Clone( "EWKinclusiveInv") hmetInverted_EWKinclusive.Add(hmetInverted_EWK_FakeTaus, 1.0) # Finalize histograms by rebinning for histogram in [ hmetBase_data, hmetInverted_data, hmetBase_EWK_GenuineTaus, hmetInverted_EWK_GenuineTaus, hmetBase_EWKinclusive, hmetBase_EWK_FakeTaus, hmetInverted_EWK_FakeTaus, hmetInverted_EWKinclusive ]: histogram.Rebin(_rebinFactor) #===== Obtain histograms for QCD (subtract MC EWK events from data) # QCD from baseline is usable only as a cross check hmetBase_QCD = hmetBase_data.Clone("QCDbase") hmetBase_QCD.Add(hmetBase_EWKinclusive, -1) hmetInverted_QCD = hmetInverted_data.Clone("QCDinv") hmetInverted_QCD.Add(hmetInverted_EWKinclusive, -1) #===== Set histograms to the templates template_EWKFakeTaus_Inverted.setHistogram( hmetInverted_EWK_FakeTaus, binLabels[i]) template_EWKGenuineTaus_Inverted.setHistogram( hmetInverted_EWK_GenuineTaus, binLabels[i]) template_EWKInclusive_Inverted.setHistogram( hmetInverted_EWKinclusive, binLabels[i]) template_QCD_Inverted.setHistogram(hmetInverted_QCD, binLabels[i]) template_EWKFakeTaus_Baseline.setHistogram(hmetBase_EWK_FakeTaus, binLabels[i]) template_EWKGenuineTaus_Baseline.setHistogram( hmetBase_EWK_GenuineTaus, binLabels[i]) template_EWKInclusive_Baseline.setHistogram( hmetBase_EWKinclusive, binLabels[i]) template_QCD_Baseline.setHistogram(hmetBase_QCD, binLabels[i]) #===== Make plots of templates manager.plotTemplates() #===== Fit individual templates to data fitOptions = "R B L W M" # RBLWM manager.calculateNormalizationCoefficients(hmetBase_data, fitOptions, FITMIN, FITMAX) #===== Calculate combined normalisation coefficient (f_fakes = w*f_QCD + (1-w)*f_EWKfakes) # Obtain histograms histoName = "ForDataDrivenCtrlPlots/shapeTransverseMass/shapeTransverseMass" + binStr dataMt = plots.DataMCPlot(dsetMgr, histoName).histoMgr.getHisto( "Data").getRootHisto().Clone(histoName) treatNegativeBins(dataMt, "Data_inverted mT") histoName = "ForDataDrivenCtrlPlotsEWKFakeTaus/shapeTransverseMass/shapeTransverseMass" + binStr ewkFakeTausMt = plots.DataMCPlot( dsetMgr, histoName).histoMgr.getHisto( "EWK").getRootHisto().Clone(histoName) treatNegativeBins(ewkFakeTausMt, "ewkFakeTaus_inverted mT") histoName = "ForDataDrivenCtrlPlotsEWKGenuineTaus/shapeTransverseMass/shapeTransverseMass" + binStr ewkGenuineTausMt = plots.DataMCPlot( dsetMgr, histoName).histoMgr.getHisto( "EWK").getRootHisto().Clone(histoName) treatNegativeBins(ewkGenuineTausMt, "ewkGenuineTaus_inverted mT") qcdMt = dataMt.Clone("QCD") qcdMt.Add(ewkFakeTausMt, -1) qcdMt.Add(ewkGenuineTausMt, -1) treatNegativeBins(qcdMt, "QCD_inverted mT") # Do calculation manager.calculateCombinedNormalizationCoefficient( qcdMt, ewkFakeTausMt) #===== Save normalization outFileName = "QCDNormalizationFactors_%s_%s.py" % (HISTONAME, moduleInfoString) outFileFullName = os.path.join(argv[1], outFileName) manager.writeScaleFactorFile(outFileFullName, moduleInfoString)
def main(argv): COMBINEDHISTODIR = "ForQCDNormalization" FAKEHISTODIR = "ForQCDNormalizationEWKFakeTaus" GENUINEHISTODIR = "ForQCDNormalizationEWKGenuineTaus" comparisonList = ["AfterStdSelections"] dirs = [] if len(sys.argv) < 2: usage() dirs.append(sys.argv[1]) # Create all dsetMgr from a multicrab task dsetMgr = dataset.getDatasetsFromMulticrabDirs(dirs, dataEra=dataEra, searchMode=searchMode, analysisName=analysis) #print dsetMgr # Check multicrab consistency consistencyCheck.checkConsistencyStandalone(dirs[0], dsetMgr, name="QCD inverted") # As we use weighted counters for MC normalisation, we have to # update the all event count to a separately defined value because # the analysis job uses skimmed pattuple as an input dsetMgr.updateNAllEventsToPUWeighted() # Read integrated luminosities of data dsetMgr from lumi.json dsetMgr.loadLuminosities() # Include only 120 mass bin of HW and HH dsetMgr dsetMgr.remove( filter(lambda name: "TTToHplus" in name and not "M120" in name, dsetMgr.getAllDatasetNames())) dsetMgr.remove( filter(lambda name: "HplusTB" in name, dsetMgr.getAllDatasetNames())) # Default merging nad ordering of data and MC dsetMgr # All data dsetMgr to "Data" # All QCD dsetMgr to "QCD" # All single top dsetMgr to "SingleTop" # WW, WZ, ZZ to "Diboson" plots.mergeRenameReorderForDataMC(dsetMgr) # Set BR(t->H) to 0.05, keep BR(H->tau) in 1 xsect.setHplusCrossSectionsToBR(dsetMgr, br_tH=0.05, br_Htaunu=1) # Merge WH and HH dsetMgr to one (for each mass bin) plots.mergeWHandHH(dsetMgr) dsetMgr.merge( "EWK", [ "TTJets", "WJetsHT", "DYJetsToLL", "SingleTop", #"Diboson" ]) # Apply TDR style style = tdrstyle.TDRStyle() style.setOptStat(True) for HISTONAME in comparisonList: BASELINETAUHISTONAME = "NormalizationMETBaselineTau" + HISTONAME + "/NormalizationMETBaselineTau" + HISTONAME INVERTEDTAUHISTONAME = "NormalizationMETInvertedTau" + HISTONAME + "/NormalizationMETInvertedTau" + HISTONAME #===== Infer binning information and labels histonames = dsetMgr.getDataset("Data").getDirectoryContent( COMBINEDHISTODIR + "/NormalizationMETBaselineTau" + HISTONAME) bins = [] binLabels = [] if histonames == None: # Assume that only inclusive bin exists name = COMBINEDHISTODIR + "/NormalizationMETBaselineTau" + HISTONAME if not dsetMgr.getDataset("Data").hasRootHisto(name): raise Exception( "Error: Cannot find histogram or directory of name '%s'!" % name) BASELINETAUHISTONAME = "NormalizationMETBaselineTau" + HISTONAME INVERTEDTAUHISTONAME = "NormalizationMETInvertedTau" + HISTONAME bins = [""] binLabels = ["Inclusive"] else: for hname in histonames: bins.append( hname.replace("NormalizationMETBaselineTau" + HISTONAME, "")) title = dsetMgr.getDataset("Data").getDatasetRootHisto( COMBINEDHISTODIR + "/" + BASELINETAUHISTONAME + "/" + hname).getHistogram().GetTitle() title = title.replace("METBaseline" + HISTONAME, "") binLabels.append(formatHistoTitle(title)) print "\nHistogram bins available", bins print "Using bins ", bins print "\nBin labels" for i in range(len(binLabels)): line = bins[i] while len(line) < 10: line += " " line += ": " + binLabels[i] print line print #===== Initialize normalization calculator invertedQCD = InvertedTauID() invertedQCD.setLumi(dsetMgr.getDataset("Data").getLuminosity()) invertedQCD.setInfo([dataEra, searchMode, HISTONAME]) #===== Loop over tau pT bins for i, binStr in enumerate(bins): print "\n********************************" print "*** Fitting bin %s" % binLabels[i] print "********************************\n" invertedQCD.resetBinResults() invertedQCD.setLabel(binLabels[i]) #===== Obtain histograms for normalization metBase = plots.DataMCPlot( dsetMgr, COMBINEDHISTODIR + "/" + BASELINETAUHISTONAME + binStr) metInver = plots.DataMCPlot( dsetMgr, COMBINEDHISTODIR + "/" + INVERTEDTAUHISTONAME + binStr) metBase_GenuineTaus = plots.DataMCPlot( dsetMgr, GENUINEHISTODIR + "/" + BASELINETAUHISTONAME + binStr) metInver_GenuineTaus = plots.DataMCPlot( dsetMgr, GENUINEHISTODIR + "/" + INVERTEDTAUHISTONAME + binStr) metBase_FakeTaus = plots.DataMCPlot( dsetMgr, FAKEHISTODIR + "/" + BASELINETAUHISTONAME + binStr) metInver_FakeTaus = plots.DataMCPlot( dsetMgr, FAKEHISTODIR + "/" + INVERTEDTAUHISTONAME + binStr) #===== Rebin histograms before subtracting RebinFactor = 2 # Aim for 10 GeV binning metBase.histoMgr.forEachHisto( lambda h: h.getRootHisto().Rebin(RebinFactor)) metInver.histoMgr.forEachHisto( lambda h: h.getRootHisto().Rebin(RebinFactor)) metBase_GenuineTaus.histoMgr.forEachHisto( lambda h: h.getRootHisto().Rebin(RebinFactor)) metInver_GenuineTaus.histoMgr.forEachHisto( lambda h: h.getRootHisto().Rebin(RebinFactor)) metBase_FakeTaus.histoMgr.forEachHisto( lambda h: h.getRootHisto().Rebin(RebinFactor)) metInver_FakeTaus.histoMgr.forEachHisto( lambda h: h.getRootHisto().Rebin(RebinFactor)) #===== Obtain templates for data and EWK metInverted_data = metInver.histoMgr.getHisto( "Data").getRootHisto().Clone(COMBINEDHISTODIR + "/" + INVERTEDTAUHISTONAME + binStr) treatHistogram(metInverted_data, "Data, inverted") metInverted_EWK_GenuineTaus = metInver_GenuineTaus.histoMgr.getHisto( "EWK").getRootHisto().Clone(GENUINEHISTODIR + "/" + INVERTEDTAUHISTONAME + binStr) treatHistogram(metInverted_EWK_GenuineTaus, "EWK genuine taus, inverted") metInverted_EWK_FakeTaus = metInver_FakeTaus.histoMgr.getHisto( "EWK").getRootHisto().Clone(FAKEHISTODIR + "/" + INVERTEDTAUHISTONAME + binStr) treatHistogram(metInverted_EWK_FakeTaus, "EWK fake taus, inverted") metBase_data = metBase.histoMgr.getHisto( "Data").getRootHisto().Clone(COMBINEDHISTODIR + "/" + BASELINETAUHISTONAME + binStr) treatHistogram(metBase_data, "Data, baseline") metBase_EWK_GenuineTaus = metBase_GenuineTaus.histoMgr.getHisto( "EWK").getRootHisto().Clone(GENUINEHISTODIR + "/" + BASELINETAUHISTONAME + binStr) treatHistogram(metBase_EWK_GenuineTaus, "EWK genuine taus, baseline") metBase_EWK_FakeTaus = metBase_FakeTaus.histoMgr.getHisto( "EWK").getRootHisto().Clone(FAKEHISTODIR + "/" + BASELINETAUHISTONAME + binStr) treatHistogram(metBase_EWK_FakeTaus, "EWK fake taus, baseline") #===== Obtain templates for QCD (subtract MC EWK events from data) # QCD from baseline is usable only as a cross check #metBase_QCD = metBase_data.Clone("QCD") #metBase_QCD.Add(metBase_EWK_GenuineTaus,-1) #metBase_QCD.Add(metBase_EWK_FakeTaus,-1) #addLabels(metBase_QCD, "QCD, baseline") metInverted_QCD = metInverted_data.Clone("QCD") metInverted_QCD.Add(metInverted_EWK_GenuineTaus, -1) metInverted_QCD.Add(metInverted_EWK_FakeTaus, -1) treatHistogram(metInverted_QCD, "QCD, inverted") #===== Make plots of templates print "\n*** Integrals of plotted templates" #invertedQCD.plotHisto(metInverted_data,"template_Data_Inverted") #invertedQCD.plotHisto(metInverted_EWK_GenuineTaus,"template_EWKGenuineTaus_Inverted") #invertedQCD.plotHisto(metInverted_EWK_FakeTaus,"template_EWKFakeTaus_Inverted") invertedQCD.plotHisto(metInverted_QCD, "template_QCD_Inverted") invertedQCD.plotHisto(metBase_data, "template_Data_Baseline") invertedQCD.plotHisto(metBase_EWK_GenuineTaus, "template_EWKGenuineTaus_Baseline") invertedQCD.plotHisto(metBase_EWK_FakeTaus, "template_EWKFakeTaus_Baseline") #invertedQCD.plotHisto(metBase_QCD,"template_QCD_Baseline") #===== Fit individual templates and # Fit first templates for QCD, EWK_genuine_taus, and EWK_fake_taus # Then fit the shape of those parametrizations to baseline data to obtain normalization coefficients fitOptions = "RB" # Strategy: take EWK templates from baseline and QCD template from inverted; then fit to baseline data invertedQCD.fitEWK_GenuineTaus(metInverted_EWK_GenuineTaus, fitOptions) invertedQCD.fitEWK_GenuineTaus(metBase_EWK_GenuineTaus, fitOptions) invertedQCD.fitEWK_FakeTaus(metInverted_EWK_FakeTaus, fitOptions) invertedQCD.fitEWK_FakeTaus(metBase_EWK_FakeTaus, fitOptions) invertedQCD.fitQCD(metInverted_QCD, fitOptions) invertedQCD.fitData(metBase_data) #===== Calculate normalization invertedQCD.getNormalization() invertedQCD.Summary() invertedQCD.WriteNormalizationToFile( "QCDInvertedNormalizationFactorsFilteredEWKFakeTaus.py") invertedQCD.WriteLatexOutput("fits.tex")
def DataMCHistograms(datasetsMgr, analysisType=""): ''' Create data-MC comparison plot, with the default: - legend labels (defined in plots._legendLabels) - plot styles (defined in plots._plotStyles, and in styles) - drawing styles ('HIST' for MC, 'EP' for data) - legend styles ('L' for MC, 'P' for data) ''' Verbose("Plotting all histograms for %s" % analysisType) # Sanity check IsBaselineOrInverted(analysisType) # Definitions histoNames = [] histoKwargs = {} saveFormats = [".png", ".pdf"] #[".C", ".png", ".pdf"] # General Settings if opts.mergeEWK: _moveLegend = {"dx": -0.05, "dy": 0.0, "dh": -0.15} else: _moveLegend = {"dx": -0.05, "dy": 0.0, "dh": 0.1} _kwargs = { "rebinX": 1, "rebinY": None, "ratioYlabel": "Data/MC", "ratio": False, "stackMCHistograms": True, "ratioInvert": False, "addMCUncertainty": False, "addLuminosityText": True, "addCmsText": True, "cmsExtraText": "Preliminary", "opts": { "ymin": 2e-1, "ymaxfactor": 10 }, #1.2 "opts2": { "ymin": 0.0, "ymax": 2.0 }, "log": True, "errorBarsX": True, "moveLegend": _moveLegend, "cutBox": { "cutValue": 0.0, "fillColor": 16, "box": False, "line": False, "greaterThan": True }, } # Create/Draw the plots histoName = "%s_TopMassReco_LdgTrijetPt_AfterAllSelections" % analysisType kwargs = copy.deepcopy(_kwargs) kwargs["ylabel"] = "Events / %.0f" histoNames.append(histoName) histoKwargs[histoName] = kwargs histoName = "%s_TopMassReco_LdgTrijetM_AfterAllSelections" % analysisType kwargs = copy.deepcopy(_kwargs) kwargs["ylabel"] = "Events / %.0f GeV/c^{2}" kwargs["log"] = False kwargs["opts"] = {"xmax": 700, "ymin": 2e-1, "ymaxfactor": 1.2} kwargs["cutBox"] = { "cutValue": 173.21, "fillColor": 16, "box": False, "line": True, "greaterThan": True } histoNames.append(histoName) histoKwargs[histoName] = kwargs histoName = "%s_TopMassReco_SubLdgTrijetPt_AfterAllSelections" % analysisType kwargs = copy.deepcopy(_kwargs) kwargs["ylabel"] = "Events / %.0f GeV/c" histoNames.append(histoName) histoKwargs[histoName] = kwargs histoName = "%s_TopMassReco_SubLdgTrijetM_AfterAllSelections" % analysisType kwargs = copy.deepcopy(_kwargs) kwargs["ylabel"] = "Events / %.0f GeV/c^{2}" kwargs["log"] = False kwargs["opts"] = {"xmax": 700, "ymin": 2e-1, "ymaxfactor": 1.2} kwargs["cutBox"] = { "cutValue": 173.21, "fillColor": 16, "box": False, "line": True, "greaterThan": True } histoNames.append(histoName) histoKwargs[histoName] = kwargs histoName = "%s_TopMassReco_LdgDijetPt_AfterAllSelections" % analysisType kwargs = copy.deepcopy(_kwargs) kwargs["ylabel"] = "Events / %.0f GeV/c" histoNames.append(histoName) histoKwargs[histoName] = kwargs histoName = "%s_TopMassReco_LdgDijetM_AfterAllSelections" % analysisType kwargs = copy.deepcopy(_kwargs) kwargs["ylabel"] = "Events / %.0f GeV/c^{2}" kwargs["cutBox"] = { "cutValue": 80.399, "fillColor": 16, "box": False, "line": True, "greaterThan": True } histoNames.append(histoName) histoKwargs[histoName] = kwargs histoName = "%s_TopMassReco_SubLdgDijetPt_AfterAllSelections" % analysisType kwargs = copy.deepcopy(_kwargs) kwargs["ylabel"] = "Events / %.0f GeV/c" histoNames.append(histoName) histoKwargs[histoName] = kwargs histoName = "%s_TopMassReco_SubLdgDijetM_AfterAllSelections" % analysisType kwargs = copy.deepcopy(_kwargs) kwargs["ylabel"] = "Events / %.0f GeV/c^{2}" kwargs["cutBox"] = { "cutValue": 80.399, "fillColor": 16, "box": False, "line": True, "greaterThan": True } histoNames.append(histoName) histoKwargs[histoName] = kwargs # For-loop: All histograms in list for histoName in histoNames: kwargs_ = histoKwargs[histoName] #saveName = os.path.join(opts.saveDir, histoName.replace("/", "_")) saveName = histoName.replace("/", "_") if opts.mcOnly: p = plots.MCPlot(datasetsMgr, histoName, normalizeToLumi=opts.intLumi, saveFormats=[]) kwargs_.pop("ratio", None) kwargs_.pop("ratioYlabel", None) kwargs_.pop("ratioInvert", None) kwargs_.pop("opts2", None) plots.drawPlot(p, saveName, **kwargs_) #the "**" unpacks the kwargs_ dictionary else: p = plots.DataMCPlot(datasetsMgr, histoName, saveFormats=[]) plots.drawPlot(p, saveName, **kwargs_) #the "**" unpacks the kwargs_ dictionary # Save plot in all formats SavePlot(p, saveName, os.path.join(opts.saveDir, "Signal", opts.optMode)) return
def main(argv, dsetMgr, moduleInfoString): COMBINEDHISTODIR = "ForQCDNormalization" FAKEHISTODIR = "ForQCDNormalizationEWKFakeTaus" GENUINEHISTODIR = "ForQCDNormalizationEWKGenuineTaus" comparisonList = ["AfterStdSelections"] dirs = [] dirs.append(sys.argv[1]) # Check multicrab consistency consistencyCheck.checkConsistencyStandalone(dirs[0], dsetMgr, name="QCD inverted") # As we use weighted counters for MC normalisation, we have to # update the all event count to a separately defined value because # the analysis job uses skimmed pattuple as an input dsetMgr.updateNAllEventsToPUWeighted() # Read integrated luminosities of data dsetMgr from lumi.json dsetMgr.loadLuminosities() # Include only 120 mass bin of HW and HH dsetMgr dsetMgr.remove( filter(lambda name: "TTToHplus" in name and not "M120" in name, dsetMgr.getAllDatasetNames())) dsetMgr.remove( filter(lambda name: "HplusTB" in name, dsetMgr.getAllDatasetNames())) # Default merging nad ordering of data and MC dsetMgr # All data dsetMgr to "Data" # All QCD dsetMgr to "QCD" # All single top dsetMgr to "SingleTop" # WW, WZ, ZZ to "Diboson" plots.mergeRenameReorderForDataMC(dsetMgr) # Set BR(t->H) to 0.05, keep BR(H->tau) in 1 xsect.setHplusCrossSectionsToBR(dsetMgr, br_tH=0.05, br_Htaunu=1) # Merge WH and HH dsetMgr to one (for each mass bin) plots.mergeWHandHH(dsetMgr) # Merge MC EWK samples as one EWK sample myMergeList = [] if "TT" in dsetMgr.getMCDatasetNames(): myMergeList.append("TT") # Powheg, no neg. weights -> large stats. else: myMergeList.append("TTJets") # Madgraph with negative weights print "Warning: using TTJets as input, but this is suboptimal. Please switch to the TT sample (much more stats.)." myMergeList.append("WJetsHT") myMergeList.append("DYJetsToLLHT") myMergeList.append("SingleTop") if "Diboson" in dsetMgr.getMCDatasetNames(): myMergeList.append("Diboson") print "Warning: ignoring diboson sample (since it does not exist) ..." for item in myMergeList: if not item in dsetMgr.getMCDatasetNames(): raise Exception( "Error: tried to use dataset '%s' as part of the merged EWK dataset, but the dataset '%s' does not exist!" % (item, item)) dsetMgr.merge("EWK", myMergeList) # Apply TDR style style = tdrstyle.TDRStyle() style.setOptStat(True) for HISTONAME in comparisonList: BASELINETAUHISTONAME = "NormalizationMETBaselineTau" + HISTONAME + "/NormalizationMETBaselineTau" + HISTONAME INVERTEDTAUHISTONAME = "NormalizationMETInvertedTau" + HISTONAME + "/NormalizationMETInvertedTau" + HISTONAME FITMIN = None FITMAX = None #===== Infer binning information and labels histonames = dsetMgr.getDataset("Data").getDirectoryContent( COMBINEDHISTODIR + "/NormalizationMETBaselineTau" + HISTONAME) bins = [] binLabels = [] if histonames == None: # Assume that only inclusive bin exists name = COMBINEDHISTODIR + "/NormalizationMETBaselineTau" + HISTONAME if not dsetMgr.getDataset("Data").hasRootHisto(name): raise Exception( "Error: Cannot find histogram or directory of name '%s'!" % name) BASELINETAUHISTONAME = "NormalizationMETBaselineTau" + HISTONAME INVERTEDTAUHISTONAME = "NormalizationMETInvertedTau" + HISTONAME bins = [""] binLabels = ["Inclusive"] else: for hname in histonames: binIndex = hname.replace( "NormalizationMETBaselineTau" + HISTONAME, "") hDummy = dsetMgr.getDataset("Data").getDatasetRootHisto( COMBINEDHISTODIR + "/" + BASELINETAUHISTONAME + binIndex).getHistogram() title = hDummy.GetTitle() title = title.replace("METBaseline" + HISTONAME, "") if hDummy.Integral() > 0.0: bins.append(binIndex) if binIndex == "Inclusive": binLabels.append(binIndex) else: binLabels.append( QCDNormalization.getModifiedBinLabelString(title)) if FITMIN == None: FITMIN = hDummy.GetXaxis().GetXmin() FITMAX = hDummy.GetXaxis().GetXmax() hDummy.Delete() else: print "Skipping bin '%s' (%s) because it has no entries" % ( binIndex, QCDNormalization.getModifiedBinLabelString(title)) print "\nHistogram bins available", bins # Select bins by filter if len(selectOnlyBins) > 0: oldBinLabels = binLabels[:] oldBins = bins[:] binLabels = [] bins = [] for k in selectOnlyBins: for i in range(len(oldBinLabels)): if k == oldBinLabels[i] or k == oldBins[i]: binLabels.append(oldBinLabels[i]) bins.append(oldBins[i]) print "Using bins ", bins print "\nBin labels" for i in range(len(binLabels)): line = bins[i] while len(line) < 10: line += " " line += ": " + binLabels[i] print line print #===== Initialize normalization calculator #manager = QCDNormalization.QCDNormalizationManagerExperimental1(binLabels) manager = QCDNormalization.QCDNormalizationManagerDefault( binLabels, dirs[0], moduleInfoString) #===== Create templates (EWK fakes, EWK genuine, QCD; data template is created by manager) template_EWKFakeTaus_Baseline = manager.createTemplate( "EWKFakeTaus_Baseline") template_EWKFakeTaus_Inverted = manager.createTemplate( "EWKFakeTaus_Inverted") template_EWKGenuineTaus_Baseline = manager.createTemplate( "EWKGenuineTaus_Baseline") template_EWKGenuineTaus_Inverted = manager.createTemplate( "EWKGenuineTaus_Inverted") template_EWKInclusive_Baseline = manager.createTemplate( "EWKInclusive_Baseline") template_EWKInclusive_Inverted = manager.createTemplate( "EWKInclusive_Inverted") template_QCD_Baseline = manager.createTemplate("QCD_Baseline") template_QCD_Inverted = manager.createTemplate("QCD_Inverted") #===== Define fit functions and fit parameters # The available functions are defined in the FitFunction class in the QCDMeasurement/python/QCDNormalization.py file # commented out fitter for EWK fake taus, since only the fit on inclusive EWK is used to obtain w_QCD #boundary = 100 #template_EWKFakeTaus_Baseline.setFitter(QCDNormalization.FitFunction("EWKFunctionInv", boundary=boundary, norm=1, rejectPoints=1), #FITMIN, FITMAX) #template_EWKFakeTaus_Baseline.setDefaultFitParam(defaultInitialValue=[10.0, 100, 45, 0.02], #defaultLowerLimit= [ 0.1, 70, 10, 0.001], #defaultUpperLimit= [ 30, 300, 100, 0.1]) # commented out fitter for EWK genuine taus, since only the fit on inclusive EWK is used to obtain w_QCD #boundary = 150 #template_EWKGenuineTaus_Baseline.setFitter(QCDNormalization.FitFunction("EWKFunction", boundary=boundary, norm=1, rejectPoints=1), #FITMIN, FITMAX) #template_EWKGenuineTaus_Baseline.setDefaultFitParam(defaultLowerLimit=[0.5, 90, 30, 0.0001], #defaultUpperLimit=[ 20, 150, 50, 1.0]) # Inclusive EWK boundary = 150 template_EWKInclusive_Baseline.setFitter( QCDNormalization.FitFunction("EWKFunction", boundary=boundary, norm=1, rejectPoints=1), FITMIN, FITMAX) template_EWKInclusive_Baseline.setDefaultFitParam( defaultLowerLimit=[0.5, 90, 30, 0.0001], defaultUpperLimit=[20, 150, 50, 1.0]) # Note that the same function is used for QCD only and QCD+EWK fakes template_QCD_Inverted.setFitter( QCDNormalization.FitFunction("QCDFunction", norm=1), FITMIN, FITMAX) template_QCD_Inverted.setDefaultFitParam( defaultLowerLimit=[0.0001, 0.001, 0.1, 0.0, 10, 0.0001, 0.001], defaultUpperLimit=[200, 10, 10, 150, 100, 1, 0.05]) #===== Loop over tau pT bins for i, binStr in enumerate(bins): print "\n********************************" print "*** Fitting bin %s" % binLabels[i] print "********************************\n" #===== Reset bin results manager.resetBinResults() #===== Obtain histograms for normalization # Data histoName = COMBINEDHISTODIR + "/" + BASELINETAUHISTONAME + binStr hmetBase_data = plots.DataMCPlot( dsetMgr, histoName).histoMgr.getHisto( "Data").getRootHisto().Clone(histoName) histoName = COMBINEDHISTODIR + "/" + INVERTEDTAUHISTONAME + binStr hmetInverted_data = plots.DataMCPlot( dsetMgr, histoName).histoMgr.getHisto( "Data").getRootHisto().Clone(histoName) # EWK genuine taus histoName = GENUINEHISTODIR + "/" + BASELINETAUHISTONAME + binStr hmetBase_EWK_GenuineTaus = plots.DataMCPlot( dsetMgr, histoName).histoMgr.getHisto( "EWK").getRootHisto().Clone(histoName) histoName = GENUINEHISTODIR + "/" + INVERTEDTAUHISTONAME + binStr hmetInverted_EWK_GenuineTaus = plots.DataMCPlot( dsetMgr, histoName).histoMgr.getHisto( "EWK").getRootHisto().Clone(histoName) # EWK fake taus histoName = FAKEHISTODIR + "/" + BASELINETAUHISTONAME + binStr hmetBase_EWK_FakeTaus = plots.DataMCPlot( dsetMgr, histoName).histoMgr.getHisto( "EWK").getRootHisto().Clone(histoName) histoName = FAKEHISTODIR + "/" + INVERTEDTAUHISTONAME + binStr hmetInverted_EWK_FakeTaus = plots.DataMCPlot( dsetMgr, histoName).histoMgr.getHisto( "EWK").getRootHisto().Clone(histoName) # Finalize histograms by rebinning for histogram in [ hmetBase_data, hmetInverted_data, hmetBase_EWK_GenuineTaus, hmetInverted_EWK_GenuineTaus, hmetBase_EWK_FakeTaus, hmetInverted_EWK_FakeTaus ]: histogram.Rebin(_rebinFactor) #===== Obtain inclusive EWK histograms hmetBase_EWKinclusive = hmetBase_EWK_GenuineTaus.Clone( "EWKinclusiveBase") hmetBase_EWKinclusive.Add(hmetBase_EWK_FakeTaus, 1.0) hmetInverted_EWKinclusive = hmetInverted_EWK_GenuineTaus.Clone( "EWKinclusiveInv") hmetInverted_EWKinclusive.Add(hmetInverted_EWK_FakeTaus, 1.0) #===== Obtain histograms for QCD (subtract MC EWK events from data) # QCD from baseline is usable only as a cross check hmetBase_QCD = hmetBase_data.Clone("QCDbase") hmetBase_QCD.Add(hmetBase_EWKinclusive, -1) hmetInverted_QCD = hmetInverted_data.Clone("QCDinv") hmetInverted_QCD.Add(hmetInverted_EWKinclusive, -1) #===== Set histograms to the templates template_EWKFakeTaus_Inverted.setHistogram( hmetInverted_EWK_FakeTaus, binLabels[i]) template_EWKGenuineTaus_Inverted.setHistogram( hmetInverted_EWK_GenuineTaus, binLabels[i]) template_EWKInclusive_Inverted.setHistogram( hmetInverted_EWKinclusive, binLabels[i]) template_QCD_Inverted.setHistogram(hmetInverted_QCD, binLabels[i]) template_EWKFakeTaus_Baseline.setHistogram(hmetBase_EWK_FakeTaus, binLabels[i]) template_EWKGenuineTaus_Baseline.setHistogram( hmetBase_EWK_GenuineTaus, binLabels[i]) template_EWKInclusive_Baseline.setHistogram( hmetBase_EWKinclusive, binLabels[i]) template_QCD_Baseline.setHistogram(hmetBase_QCD, binLabels[i]) #===== Make plots of templates manager.plotTemplates() #===== Fit individual templates to data fitOptions = "R B" # RBLW manager.calculateNormalizationCoefficients(hmetBase_data, fitOptions, FITMIN, FITMAX) #===== Calculate combined normalisation coefficient (f_fakes = w*f_QCD + (1-w)*f_EWKfakes) # Obtain histograms histoName = "ForDataDrivenCtrlPlots/shapeTransverseMass/shapeTransverseMass" + binStr dataMt = plots.DataMCPlot(dsetMgr, histoName).histoMgr.getHisto( "Data").getRootHisto().Clone(histoName) treatNegativeBins(dataMt, "Data_inverted mT") histoName = "ForDataDrivenCtrlPlotsEWKFakeTaus/shapeTransverseMass/shapeTransverseMass" + binStr ewkFakeTausMt = plots.DataMCPlot( dsetMgr, histoName).histoMgr.getHisto( "EWK").getRootHisto().Clone(histoName) treatNegativeBins(ewkFakeTausMt, "ewkFakeTaus_inverted mT") histoName = "ForDataDrivenCtrlPlotsEWKGenuineTaus/shapeTransverseMass/shapeTransverseMass" + binStr ewkGenuineTausMt = plots.DataMCPlot( dsetMgr, histoName).histoMgr.getHisto( "EWK").getRootHisto().Clone(histoName) treatNegativeBins(ewkGenuineTausMt, "ewkGenuineTaus_inverted mT") qcdMt = dataMt.Clone("QCD") qcdMt.Add(ewkFakeTausMt, -1) qcdMt.Add(ewkGenuineTausMt, -1) treatNegativeBins(qcdMt, "QCD_inverted mT") # Do calculation manager.calculateCombinedNormalizationCoefficient( qcdMt, ewkFakeTausMt) #===== Save normalization outFileName = "QCDNormalizationFactors_%s_%s.py" % (HISTONAME, moduleInfoString) print argv[1], outFileName outFileFullName = os.path.join(argv[1], outFileName) manager.writeScaleFactorFile(outFileFullName, moduleInfoString)
def PlotSignal(datasetsMgr, analysisType, opts): ''' Create data-MC comparison plot, with the default: - legend labels (defined in plots._legendLabels) - plot styles (defined in plots._plotStyles, and in styles) - drawing styles ('HIST' for MC, 'EP' for data) - legend styles ('L' for MC, 'P' for data) ''' Verbose("Plotting histograms for %s" % analysisType) # Sanity check IsBaselineOrInverted(analysisType) # Definitions histoNames = GetHistoList(analysisType) histoKwargs = {} saveFormats = [".C", ".png", ".pdf"] # General Settings _moveLegend = {"dx": -0.1, "dy": 0.0, "dh": -0.15} logY = True if logY: _opts1 = {"ymin": 1.0, "ymaxfactor": 10} else: _opts1 = {"ymin": 0.0, "ymaxfactor": 1.2} _opts2 = {"ymin": 0.0, "ymax": 2.0}, _kwargs = { "rebinX": 10, "rebinY": None, "ratioYlabel": "Data/MC", "ratio": False, "stackMCHistograms": True, "ratioInvert": False, "addMCUncertainty": False, "addLuminosityText": True, "addCmsText": True, "cmsExtraText": "Preliminary", "opts": _opts1, "opts2": _opts2, "log": logY, "errorBarsX": True, "moveLegend": _moveLegend, "cutBox": { "cutValue": 0.0, "fillColor": 16, "box": False, "line": False, "greaterThan": True }, "ylabel": "Events / %.0f", } # Create/Draw the plots for histoName in histoNames: if "trijetm" in histoName.lower(): units = "GeV/c^{2}" format = "%0.0f " + units _kwargs["rebinX"] = 2 _kwargs["xlabel"] = "m_{jjb} (%s)" % units _kwargs["ylabel"] = "Events / %s" % (format) _kwargs["cutBox"] = { "cutValue": 173.21, "fillColor": 16, "box": False, "line": True, "greaterThan": True } _kwargs["xmax"] = 1500.0 histoKwargs[histoName] = _kwargs # For-loop: All histograms in list folder = "topSelection_" for histoName in histoNames: kwargs_ = histoKwargs[histoName] saveName = histoName.replace(folder + analysisType + "/", "") # Create the plot p = plots.DataMCPlot(datasetsMgr, histoName, saveFormats=[]) plots.drawPlot(p, saveName, **kwargs_) #the "**" unpacks the kwargs_ dictionary # Save plot in all formats SavePlot(p, histoName, os.path.join(opts.saveDir, "Signal", opts.optMode)) return