]> git.uio.no Git - u/mrichter/AliRoot.git/commitdiff
Some fixes for the QA train:
authorcholm <cholm@f7af4fe6-9843-0410-8265-dc069ae4e863>
Wed, 5 Oct 2011 13:37:41 +0000 (13:37 +0000)
committercholm <cholm@f7af4fe6-9843-0410-8265-dc069ae4e863>
Wed, 5 Oct 2011 13:37:41 +0000 (13:37 +0000)
- Event inspector writes run number to histogram file
- ForwardQA task does a little debugging - if enabled
- Energy fitter now produces another histogram with number
  of available, empty, low statistics, candidate, and
  actually fitted energy loss spectra
- Script to add task sets up output container in "trending.root"
- Sharing filter has more information in the output
- MC event inspector updated to fit interface
- Clean-up in ForwardAODConfig.C
- (Shell) script to get output of QA train

12 files changed:
PWG2/FORWARD/analysis2/AddTaskForwardQA.C
PWG2/FORWARD/analysis2/AliFMDEnergyFitter.cxx
PWG2/FORWARD/analysis2/AliFMDEventInspector.cxx
PWG2/FORWARD/analysis2/AliFMDEventInspector.h
PWG2/FORWARD/analysis2/AliFMDMCEventInspector.cxx
PWG2/FORWARD/analysis2/AliFMDMCEventInspector.h
PWG2/FORWARD/analysis2/AliFMDSharingFilter.cxx
PWG2/FORWARD/analysis2/AliForwardQATask.cxx
PWG2/FORWARD/analysis2/AliForwardQATask.h
PWG2/FORWARD/analysis2/ForwardAODConfig.C
PWG2/FORWARD/analysis2/qa/getQAResults.sh [new file with mode: 0755]
PWG2/FORWARD/analysis2/scripts/ExtractData.C [new file with mode: 0644]

index 4fee51a7448de779aef61d4b5e8bc8d366bc3198..1fdb44df3a8e071bc8e4b46cfa860621216004b6 100644 (file)
@@ -34,19 +34,25 @@ AddTaskForwardQA(Bool_t mc=false, Bool_t useCent=false)
   
   // --- Make the task and add it to the manager ---------------------
   AliForwardQATask* task = new AliForwardQATask("forwardQA");
-  // task->SetBLow(blow);
-  // task->SetBLow(bhigh);
   mgr->AddTask(task);
 
+
+  // --- Cuts --------------------------------------------------------
+  // Old style cuts
   Double_t nXi = mc ? 2 : 2;   //HHD test
   Bool_t   includeSigma = false; //true;
-
+  // High cuts for sharing filter
+  AliFMDMultCuts cHigh;
+  cHigh.SetMPVFraction(0.7);
+  cHigh.SetMultCuts(-1);
+  // Low cuts for sharing and density calculator
+  AliFMDMultCuts cLow;
+  cLow.SetMultCuts(0.1, 0.1, 0.12, 0.1, 0.12);
+  // Density cuts
   AliFMDMultCuts cDensity;
-  //c2.SetNXi(mc ? 1 : 1);
-  //  c2.SetIncludeSigma(false);
-  //c2.SetMPVFraction(0.5);
-  //Double_t factor = 1.2;
-  cDensity.SetMultCuts(0.3, 0.3, 0.3, 0.3, 0.3);
+  cDensity.SetMPVFraction(0.7);
+  cDensity.SetMultCuts(-1);
+
   
   // --- Set parameters on the algorithms ----------------------------
   // Set the number of SPD tracklets for which we consider the event a
@@ -54,6 +60,8 @@ AddTaskForwardQA(Bool_t mc=false, Bool_t useCent=false)
   task->GetEventInspector().SetLowFluxCut(1000); 
   // Set the maximum error on v_z [cm]
   task->GetEventInspector().SetMaxVzErr(0.2);
+  // Disable use of code from 1st Physics
+  task->GetEventInspector().SetUseFirstPhysicsVtx(kFALSE);
 
   // --- Set parameters on energy loss fitter ------------------------
   // Set the eta axis to use - note, this overrides whatever is used
@@ -85,27 +93,34 @@ AddTaskForwardQA(Bool_t mc=false, Bool_t useCent=false)
   // Disable use of angle corrected signals in the algorithm 
   task->GetSharingFilter().SetZeroSharedHitsBelowThreshold(false);
   // Enable use of angle corrected signals in the algorithm 
-  task->GetSharingFilter().GetHCuts().SetMultCuts(-1);
+  task->GetSharingFilter().SetHCuts(cHigh);
+  // Multiplicity cut 
+  // task->GetSharingFilter().GetHCuts().SetMultCuts(-1);
   // Set the number of xi's (width of landau peak) to stop at 
-  task->GetSharingFilter().GetHCuts().SetNXi(nXi);
+  // task->GetSharingFilter().GetHCuts().SetNXi(nXi);
   // Set whether or not to include sigma in cut
-  task->GetSharingFilter().GetHCuts().SetIncludeSigma(includeSigma);
-  // Enable use of angle corrected signals in the algorithm 
-  task->GetSharingFilter().SetLCuts(cDensity);
+  // task->GetSharingFilter().GetHCuts().SetIncludeSigma(includeSigma);
+  // Lower cuts from object
+  task->GetSharingFilter().SetLCuts(cLow);
+  // Use simplified sharing algorithm 
+  task->GetSharingFilter().SetUseSimpleSharing(kTRUE);
 
   // --- Density calculator ------------------------------------------
   // Set the maximum number of particle to try to reconstruct 
-  task->GetDensityCalculator().SetMaxParticles(10);
+  task->GetDensityCalculator().SetMaxParticles(3);
   // Wet whether to use poisson statistics to estimate N_ch
   task->GetDensityCalculator().SetUsePoisson(true);
+  // How to lump for Poisson calculator - 64 strips, 4 regions
+  task->GetDensityCalculator().SetLumping(64,4);
   // Set whether or not to include sigma in cut
   task->GetDensityCalculator().SetCuts(cDensity);
   // Set whether or not to use the phi acceptance
   //   AliFMDDensityCalculator::kPhiNoCorrect
   //   AliFMDDensityCalculator::kPhiCorrectNch
   //   AliFMDDensityCalculator::kPhiCorrectELoss
-  task->GetDensityCalculator()
-    .SetUsePhiAcceptance(AliFMDDensityCalculator::kPhiCorrectNch);
+  task->GetDensityCalculator().
+    SetUsePhiAcceptance(AliFMDDensityCalculator::kPhiNoCorrect);
+
   // --- Set limits on fits the energy -------------------------------
   // Maximum relative error on parameters 
   AliFMDCorrELossFit::ELossFit::fgMaxRelError = .12;
@@ -113,6 +128,10 @@ AddTaskForwardQA(Bool_t mc=false, Bool_t useCent=false)
   AliFMDCorrELossFit::ELossFit::fgLeastWeight = 1e-5;
   // Maximum value of reduced chi^2 
   AliFMDCorrELossFit::ELossFit::fgMaxChi2nu   = 20;
+
+  // --- Debug -------------------------------------------------------
+  // Set the overall debug level (1: some output, 3: a lot of output)
+  task->SetDebug(3);
     
   // --- Make the output container and connect it --------------------
   // TString outputfile = ;
@@ -125,11 +144,14 @@ AddTaskForwardQA(Bool_t mc=false, Bool_t useCent=false)
   AliAnalysisDataContainer *output = 
     mgr->CreateContainer("ForwardResults", TList::Class(), 
                         AliAnalysisManager::kParamContainer, 
-                        AliAnalysisManager::GetCommonFileName());
+                        "trending.root");
+                        // AliAnalysisManager::GetCommonFileName());
   mgr->ConnectInput(task, 0, mgr->GetCommonInputContainer());
   mgr->ConnectOutput(task, 1, histOut);
   mgr->ConnectOutput(task, 2, output);
 
-
   return task;
 }
+//
+// EOF
+// 
index 8c7eb80e004ca4aa33c8106c21492eecc8d33776..efcce5232c02688799f00fd53d6aafb36de7056b 100644 (file)
@@ -913,10 +913,16 @@ AliFMDEnergyFitter::RingHistos::Fit(TList*           dir,
   Int_t nDists = dists->GetEntries();
   Int_t low    = nDists;
   Int_t high   = 0;
+  Int_t nEmpty = 0;
+  Int_t nLow   = 0;
+  Int_t nFitted= 0;
   for (Int_t i = 0; i < nDists; i++) { 
     TH1D* dist = static_cast<TH1D*>(dists->At(i));
     // Ignore empty histograms altoghether 
-    if (!dist || dist->GetEntries() <= 0) continue; 
+    if (!dist || dist->GetEntries() <= 0) { 
+      nEmpty++;
+      continue;
+    }
 
     // Scale to the bin-width
     dist->Scale(1., "width");
@@ -927,10 +933,11 @@ AliFMDEnergyFitter::RingHistos::Fit(TList*           dir,
     dist->Scale(1/max);
     
     // Check that we have enough entries 
-    if (dist->GetEntries() <= minEntries) { 
+    Int_t nEntries = Int_t(dist->GetEntries());
+    if (nEntries <= minEntries) { 
       AliWarning(Form("Histogram at %3d (%s) has too few entries (%d <= %d)",
-                     i, dist->GetName(), Int_t(dist->GetEntries()), 
-                     minEntries));
+                     i, dist->GetName(), nEntries, minEntries));
+      nLow++;
       continue;
     }
 
@@ -938,6 +945,7 @@ AliFMDEnergyFitter::RingHistos::Fit(TList*           dir,
     TF1* res = FitHist(dist,lowCut,nParticles,minusBins,
                       relErrorCut,chi2nuCut);
     if (!res) continue;
+    nFitted++;
     // dist->GetListOfFunctions()->Add(res);
 
     // Store eta limits 
@@ -970,6 +978,29 @@ AliFMDEnergyFitter::RingHistos::Fit(TList*           dir,
       hA[j]->SetBinError(i+1, res->GetParError(kA+j));
     }
   }
+  printf("%s: Out of %d histograms, %d where empty, %d had too little data,"
+        "leaving %d to be fitted, of which %d succeeded\n",  
+        GetName(), nDists, nEmpty, nLow, nDists-nEmpty-nLow, nFitted);
+
+  TH1* status = new TH1I("status", "Status of Fits", 5, 0, 5);
+  status->GetXaxis()->SetBinLabel(1, "Total");
+  status->GetXaxis()->SetBinLabel(2, "Empty");
+  status->GetXaxis()->SetBinLabel(3, Form("<%d", minEntries));
+  status->GetXaxis()->SetBinLabel(4, "Candidates");
+  status->GetXaxis()->SetBinLabel(5, "Fitted");
+  status->SetXTitle("Status");
+  status->SetYTitle("# of #Delta distributions");
+  status->SetBinContent(1, nDists);
+  status->SetBinContent(2, nEmpty);
+  status->SetBinContent(3, nLow);
+  status->SetBinContent(4, nDists-nLow-nEmpty);
+  status->SetBinContent(5, nFitted);
+  status->SetFillColor(Color());
+  status->SetFillStyle(3001);
+  status->SetLineColor(Color());
+  status->SetDirectory(0);
+  status->SetStats(0);
+  pars->Add(status);
 
   // Fit the full-ring histogram 
   TH1* total = GetOutputHist(l, Form("%s_edist", fName.Data()));
index 71764d6dc0e9e42993393d2a18ea37d691666fa8..ba81ed383b56af96b27ebf80722b10247a16ec3d 100644 (file)
@@ -337,7 +337,7 @@ AliFMDEventInspector::Init(const TAxis& vtxAxis)
 
 //____________________________________________________________________
 void
-AliFMDEventInspector::StoreInformation()
+AliFMDEventInspector::StoreInformation(Int_t runNo)
 {
   // Write TNamed objects to output list containing information about
   // the running conditions 
@@ -346,16 +346,19 @@ AliFMDEventInspector::StoreInformation()
   TNamed* sys = new TNamed("sys", "");
   TNamed* sNN = new TNamed("sNN", "");
   TNamed* fld = new TNamed("field", "");
+  TNamed* run = new TNamed("runNo", Form("%d", runNo));
   sys->SetTitle(AliForwardUtil::CollisionSystemString(fCollisionSystem));
   sNN->SetTitle(AliForwardUtil::CenterOfMassEnergyString(fEnergy));
   fld->SetTitle(AliForwardUtil::MagneticFieldString(fField));
   sys->SetUniqueID(fCollisionSystem);
   sNN->SetUniqueID(fEnergy);
   fld->SetUniqueID(fField);
+  run->SetUniqueID(runNo);
 
   fList->Add(sys);
   fList->Add(sNN);
   fList->Add(fld);
+  fList->Add(run);
 }
 
 //____________________________________________________________________
@@ -851,7 +854,7 @@ AliFMDEventInspector::ReadRunDetails(const AliESDEvent* esd)
   fField           = 
     AliForwardUtil::ParseMagneticField(esd->GetMagneticField());
 
-  StoreInformation();
+  StoreInformation(esd->GetRunNumber());
   if (fCollisionSystem   == AliForwardUtil::kUnknown || 
       fEnergy            <= 0                        || 
       TMath::Abs(fField) >  10) 
index d5e7436cb642376f29790550bb7c767b42c9b7b8..f6cb3cf9526edada0ad1b287822dd3d711278d28 100644 (file)
@@ -237,9 +237,11 @@ public:
    * - sys   Contains the collision system string and identifier. 
    * - sNN   Contains the center-of-mass energy per nucleon (GeV)
    * - field Contains the L3 magnetic field (kG)
+   * - run   Contains the run number
    * 
+   * @param runNo Run number - read off from ESD event
    */
-  virtual void StoreInformation();
+  virtual void StoreInformation(Int_t runNo);
 protected:
   /** 
    * Read the trigger information from the ESD event 
index 6ced6d8c17676aa2ed373c71278570340aa791b0..3e64b651df92d29339405c068ad6b9381ea1c885 100644 (file)
@@ -222,11 +222,11 @@ AliFMDMCEventInspector::Init(const TAxis& vtxAxis)
 
 //____________________________________________________________________
 void
-AliFMDMCEventInspector::StoreInformation()
+AliFMDMCEventInspector::StoreInformation(Int_t runNo)
 {
   // Store information about running conditions in the output list 
   if (!fList) return;
-  AliFMDEventInspector::StoreInformation();
+  AliFMDEventInspector::StoreInformation(runNo);
   TNamed* mc = new TNamed("mc", fProduction.Data());
   mc->SetUniqueID(1);
   fList->Add(mc);
index c339c8c9bb90c5dd1534807aed8b1e1dbdc3ea0f..1e861c7e369f1d3ff3814f4e2a90f0e1dc8a3347 100644 (file)
@@ -125,8 +125,10 @@ public:
    * The presence of this indicate MC data.
    *
    * - mc    Nothing special, and unique id is 1
+   * 
+   * @param runNo Run number 
    */
-  virtual void StoreInformation();
+  virtual void StoreInformation(Int_t runNo);
   /** 
    * Read the production details 
    * 
index 789f76a13ea84ca1b820a26050e5f3d81765fd18..978a1d926f9bf990ef0c9c5abcaea26f2ad692fa 100644 (file)
@@ -1025,8 +1025,8 @@ AliFMDSharingFilter::RingHistos::RingHistos(UShort_t d, Char_t r)
   //    d detector
   //    r ring 
   //
-  fBefore = new TH1D("esdEloss", "Energy loss (reconstruction)", 
-                    600, 0, 15);
+  fBefore = new TH1D("esdEloss", Form("Energy loss in %s (reconstruction)", 
+                                     GetName()), 600, 0, 15);
   fBefore->SetXTitle("#Delta E/#Delta E_{mip}");
   fBefore->SetYTitle("P(#Delta E/#Delta E_{mip})");
   fBefore->SetFillColor(Color());
@@ -1036,39 +1036,29 @@ AliFMDSharingFilter::RingHistos::RingHistos(UShort_t d, Char_t r)
   fBefore->SetDirectory(0);
 
   fAfter  = static_cast<TH1D*>(fBefore->Clone("anaEloss"));
-  fAfter->SetTitle("Energy loss in %s (sharing corrected)");
+  fAfter->SetTitle(Form("Energy loss in %s (sharing corrected)", GetName()));
   fAfter->SetFillColor(Color()+2);
   fAfter->SetLineStyle(1);
   fAfter->SetDirectory(0);
   
   fSingle = new TH1D("singleEloss", "Energy loss (single strips)", 
                     600, 0, 15);
-  fSingle->SetXTitle("#Delta E/#Delta E_{mip}");
-  fSingle->SetYTitle("P(#Delta E/#Delta E_{mip})");
-  fSingle->SetFillColor(kMagenta);
+  fSingle->SetXTitle("#Delta/#Delta_{mip}");
+  fSingle->SetYTitle("P(#Delta/#Delta_{mip})");
+  fSingle->SetFillColor(Color());
   fSingle->SetFillStyle(3001);
   fSingle->SetLineColor(kBlack);
   fSingle->SetLineStyle(2);
   fSingle->SetDirectory(0);
 
-  fDouble = new TH1D("doubleEloss", "Energy loss (two strips)", 
-                    600, 0, 15);
-  fDouble->SetXTitle("#Delta E/#Delta E_{mip}");
-  fDouble->SetYTitle("P(#Delta E/#Delta E_{mip})");
-  fDouble->SetFillColor(kMagenta+1);
-  fDouble->SetFillStyle(3001);
-  fDouble->SetLineColor(kBlack);
-  fDouble->SetLineStyle(2);
+  fDouble = static_cast<TH1D*>(fSingle->Clone("doubleEloss"));
+  fDouble->SetTitle("Energy loss (two strips)");
+  fDouble->SetFillColor(Color()+1);
   fDouble->SetDirectory(0);
-
-  fTriple = new TH1D("tripleEloss", "Energy loss (three strips)", 
-                    600, 0, 15);
-  fTriple->SetXTitle("#Delta E/#Delta E_{mip}");
-  fTriple->SetYTitle("P(#Delta E/#Delta E_{mip})");
-  fTriple->SetFillColor(kMagenta+2);
-  fTriple->SetFillStyle(3001);
-  fTriple->SetLineColor(kBlack);
-  fTriple->SetLineStyle(2);
+  
+  fTriple = static_cast<TH1D*>(fSingle->Clone("tripleEloss"));
+  fTriple->SetTitle("Energy loss (three strips)"); 
+  fTriple->SetFillColor(Color()+2);
   fTriple->SetDirectory(0);
   
   //Int_t nBinsForInner = (r == 'I' ? 32 : 16);
@@ -1077,13 +1067,13 @@ AliFMDSharingFilter::RingHistos::RingHistos(UShort_t d, Char_t r)
   
   fSinglePerStrip = new TH2D("singlePerStrip", "SinglePerStrip", 
                             600,0,15, nBinsForInner,0,nStrips);
-  fSinglePerStrip->SetXTitle("Eloss");
-  fSinglePerStrip->SetYTitle("Strip");
+  fSinglePerStrip->SetXTitle("#Delta/#Delta_{mip}");
+  fSinglePerStrip->SetYTitle("Strip #");
   fSinglePerStrip->SetZTitle("Counts");
   fSinglePerStrip->SetDirectory(0);
 
   fDistanceBefore = new TH1D("distanceBefore", "Distance before sharing", 
-                           nStrips , 0,nStrips );
+                            nStrips , 0,nStrips );
   fDistanceBefore->SetXTitle("Distance");
   fDistanceBefore->SetYTitle("Counts");
   fDistanceBefore->SetFillColor(kGreen+2);
@@ -1092,14 +1082,9 @@ AliFMDSharingFilter::RingHistos::RingHistos(UShort_t d, Char_t r)
   fDistanceBefore->SetLineStyle(2);
   fDistanceBefore->SetDirectory(0);
 
-  fDistanceAfter = new TH1D("distanceAfter", "Distance after sharing", 
-                           nStrips , 0,nStrips );
-  fDistanceAfter->SetXTitle("Distance");
-  fDistanceAfter->SetYTitle("Counts");
+  fDistanceAfter = static_cast<TH1D*>(fDistanceBefore->Clone("distanceAfter"));
+  fDistanceAfter->SetTitle("Distance after sharing"); 
   fDistanceAfter->SetFillColor(kGreen+1);
-  fDistanceAfter->SetFillStyle(3001);
-  fDistanceAfter->SetLineColor(kBlack);
-  fDistanceAfter->SetLineStyle(2);
   fDistanceAfter->SetDirectory(0);
 
   
index 40e76c2b004ae9491fa4a5c2d544f3d0accebbaa..a2e16ffdf05ab3a84849ad56319214a704669b8b 100644 (file)
@@ -41,7 +41,8 @@ AliForwardQATask::AliForwardQATask()
     fEnergyFitter(),
     fSharingFilter(),
     fDensityCalculator(),
-    fList(0)
+    fList(0),
+    fDebug(0)
 {
   // 
   // Constructor
@@ -60,7 +61,8 @@ AliForwardQATask::AliForwardQATask(const char* name)
     fEnergyFitter("energy"),
     fSharingFilter("sharing"), 
     fDensityCalculator("density"),
-    fList(0)
+    fList(0),
+    fDebug(0)
 {
   // 
   // Constructor 
@@ -92,7 +94,8 @@ AliForwardQATask::AliForwardQATask(const AliForwardQATask& o)
     fEnergyFitter(o.fEnergyFitter),
     fSharingFilter(o.fSharingFilter),
     fDensityCalculator(o.fDensityCalculator),
-    fList(o.fList) 
+    fList(o.fList),
+    fDebug(o.fDebug) 
 {
   // 
   // Copy constructor 
@@ -128,6 +131,7 @@ AliForwardQATask::operator=(const AliForwardQATask& o)
   fDensityCalculator = o.fDensityCalculator;
   fHistos            = o.fHistos;
   fList              = o.fList;
+  fDebug             = o.fDebug;
 
   return *this;
 }
@@ -142,6 +146,7 @@ AliForwardQATask::SetDebug(Int_t dbg)
   // Parameters:
   //    dbg Debug level
   //
+  fDebug = dbg;
   fEventInspector.SetDebug(dbg);
   fEnergyFitter.SetDebug(dbg);
   fSharingFilter.SetDebug(dbg);
@@ -389,6 +394,7 @@ AliForwardQATask::Terminate(Option_t*)
   // Parameters:
   //    option Not used 
   //
+  if (fDebug) AliInfo("In Forwards terminate");
   TStopwatch swt;
   swt.Start();
 
@@ -424,6 +430,8 @@ AliForwardQATask::Terminate(Option_t*)
   // Make a deep copy and post that as output 2 
   TList* list2 = static_cast<TList*>(list->Clone(Form("%sResults", 
                                                      list->GetName())));
+  if (fDebug) AliInfoF("Posting post processing results to %s", 
+                      list2->GetName());
   list2->SetOwner();
   PostData(2, list2);
 
index c4c312dfd2734c1a78a42f143d89ebea2a43a791..7fda12f1b8134fb69b04c3f031a67cc8e9ae5c37 100644 (file)
@@ -201,6 +201,7 @@ protected:
   AliFMDDensityCalculator fDensityCalculator; // Algorithm
 
   TList* fList; // Output list 
+  Int_t fDebug; // Debug flag
 
   ClassDef(AliForwardQATask,1) // Forward QA class
 };
index 338441d32442fb2554e3cae31f6b58829d45b605..d673bee9e8054460d692e6a48b7f139649bfdfff 100644 (file)
@@ -48,10 +48,8 @@ ForwardAODConfig(AliForwardMultiplicityBase* task)
   //c.SetNXi(mc ? 1 : 1);
   //c.SetIncludeSigma(true);
   //c.SetMPVFraction(0.5);
-  
   Double_t factor = 1.;
   //if(mc) factor = 1.15;
-  
   cSharing.SetMultCuts(0.3, 0.3, 0.3, 0.3, 0.3);
  
   AliFMDMultCuts cDensity;
@@ -79,7 +77,6 @@ ForwardAODConfig(AliForwardMultiplicityBase* task)
   // Disable use of angle corrected signals in the algorithm 
   task->GetSharingFilter().SetZeroSharedHitsBelowThreshold(false);
   // Enable use of angle corrected signals in the algorithm 
-  
   task->GetSharingFilter().GetHCuts().SetMultCuts(-1);
   // Set the number of xi's (width of landau peak) to stop at 
   task->GetSharingFilter().GetHCuts().SetNXi(nXi);
@@ -89,12 +86,11 @@ ForwardAODConfig(AliForwardMultiplicityBase* task)
   task->GetSharingFilter().SetLCuts(cSharing);
   
    
-  // --- Density calculator 
+  // --- Density calculator ------------------------------------------
   // Set the maximum number of particle to try to reconstruct 
   task->GetDensityCalculator().SetMaxParticles(10);
   // Wet whether to use poisson statistics to estimate N_ch
   task->GetDensityCalculator().SetUsePoisson(true);
-
   // Set whether or not to include sigma in cut
   task->GetDensityCalculator().SetCuts(cDensity);
   
diff --git a/PWG2/FORWARD/analysis2/qa/getQAResults.sh b/PWG2/FORWARD/analysis2/qa/getQAResults.sh
new file mode 100755 (executable)
index 0000000..40b412a
--- /dev/null
@@ -0,0 +1,211 @@
+#!/bin/bash
+
+# --------------------------------------------------------------------
+uid=`id -u`
+genv_file=/tmp/gclient_env_${uid}
+
+if test ! -f ${genv_file} ; then 
+    echo "No such file: ${genv_file}, please do alien-token-init" >/dev/stderr
+    exit 1
+fi
+alien-token-info | grep -q "Token is still valid"
+if test $? -ne 0 ; then 
+    echo "Token not valid, please re-new" > /dev/stderr 
+    exit 1
+fi
+
+# --------------------------------------------------------------------
+verb=0
+
+mess()
+{
+    if test $verb -lt 1 ; then return ; fi 
+    echo $@
+}
+
+# --------------------------------------------------------------------
+usage()
+{
+    cat <<EOF
+Usage: $0 -p PRODUCTION [OPTIONS]
+
+Options: 
+       -h,--help                     This help 
+       -v,--verbose                  Be verbose
+       -p,--production  IDENTIFIER   Production identifier [$prod]
+       -y,--year        YEAR         Year of production [$year]
+       -P,--pass        NUMBER       Reconstruction pass number [$pass]
+       -d,--destination DIRECTORY    Directory to store result in [$dest] 
+       -r,--run         NUMBER       Run number [$runn]
+       -q,--qa          NUMBER       QA number 
+       -a,--archives                 Get ZIP archives 
+       -n,--no-action                Run dry (do not copy files)
+
+If run number is set, get the parts of next-to-last merge of that run only.
+
+EOF
+}
+
+# --------------------------------------------------------------------
+check_file()
+{
+    inp=$1 
+    scr=`mktemp -u Check_XXXXXXXX` 
+    cat <<EOF > ${scr}.C  
+void ${scr}() 
+{
+  gSystem->Load("libANALYSIS");
+  gSystem->Load("libANALYSISalice");
+  gSystem->Load("libTENDER");
+  // gSystem->Load("libTENDERSupplies");
+  gSystem->Load("libPWG1");
+  gSystem->Load("libPWG3base");
+  TFile* file = TFile::Open("${inp}", "READ");
+  if (!file) { 
+    Error("${scr}", "No such file ${inp}");
+    exit(1);
+    return false;
+  }
+  TObject* forward1 = file->Get("Forward");
+  if (!forward1) {
+    Error("${scr}", "No Forward object found in ${inp}");
+    exit(2);
+    ret = false;
+  } 
+  TObject* forward2 = file->Get("ForwardResults");
+  if (!forward2) {
+    Error("${scr}", "No ForwardResults object found in ${inp}");
+    exit(4);
+  } 
+  exit(0);
+}
+EOF
+    # cat ${scr}.C 
+    mess -n "aliroot -l -b -q ${scr}.C "
+    aliroot -l -b -q ${scr}.C > /dev/null 2>&1 
+    ret=$? 
+    mess "-> $ret (0: good, 1: no file, 2: no Forward, 4: no ForwardResults"
+    rm -f ${scr}.C 
+    return $ret
+}
+
+# --------------------------------------------------------------------
+year=
+prod=
+pass=1
+qual=
+dest=.
+runn=0
+qano=0
+noac=0
+arch=0
+
+while test $# -gt 0 ; do 
+    case $1 in 
+       -h|--help)        usage   ; exit 0 ;; 
+       -v|--verbose)     let verb=$verb+1  ;; 
+       -p|--production)  prod=$2 ; shift ;; 
+       -P|--pass)        pass=$2 ; shift ;; 
+       -Q|--prepass)     qual=$2 ; shift ;; 
+       -y|--year)        year=$2 ; shift ;; 
+       -d|--destination) dest=$2 ; shift ;; 
+       -r|--run)         runn=$2 ; shift ;; 
+       -q|--qa)          qano=$2 ; shift ;; 
+       -n|--no-action)   noac=1  ;; 
+       -a|--archives)    arch=1  ;; 
+       *) echo "$0: Unknown option $1" > /dev/stderr ; exit 2 ;; 
+    esac
+    shift
+done
+
+# --------------------------------------------------------------------
+if test "x$prod" = "x" ; then 
+    echo "No production identifier given" > /dev/stderr 
+    exit 2
+fi
+
+if test "x$year" = "x" ; then 
+    year=`echo $prod | sed -e 's/LHC\(..\).*/\1/'` 
+    if test "x$year" = "x" ; then 
+       echo "Couldn't get year from production identifier $prod" > /dev/stderr
+       exit 2
+    fi
+fi
+
+redir="/dev/null"
+if test $verb -gt 1 ; then redir1=/dev/stderr ; fi
+
+# --------------------------------------------------------------------
+path=/alice/data/20${year}/${prod}/
+store=${dest}/${prod}/${qual}pass${pass}
+search="ESDs/${qual}pass${pass}/"
+if test $runn -gt 0 ; then 
+    path=`printf "${path}%09d/ESDs/${qual}pass${pass}/" $runn` 
+    store=`printf "${store}/%09d" $runn` 
+    search=
+fi
+if test $qano -gt 0 ; then 
+    path=`printf "%sQA%02d/" $path $qano` 
+fi
+if test $arch -gt 0 ; then 
+    search="${search}QA_archive.zip"
+else
+    search="${search}QAresults.root"
+fi
+
+cat <<EOF
+Settings:
+
+       Production:             $prod
+       Year:                   $year
+       Pass:                   $pass
+       Pass qualifier:         $qual
+       Path:                   $path
+       Destination:            $dest
+       Store:                  $store
+       Run number:             $runn
+       Search string:          $search
+EOF
+    
+# --------------------------------------------------------------------
+mkdir -p ${store}
+mess "alien_find ${path} ${search}"
+files=`alien_find ${path} ${search} | grep -v "files found" 2> ${redir}` 
+j=0
+runs=
+for i in $files ; do 
+    b=`echo $i | sed -e "s,${path},,"` 
+    d=
+    if test $runn -gt 0 ; then 
+       r=`echo $b | sed -e "s,[0-9]*${runn}\([0-9.]*\)/.*,\1," | tr '.' '_'`
+       if test $arch -lt 1 ; then 
+           o=${store}/QAresults_${r}.zip
+       else
+           d=${store}/${r}
+           mkdir -p $d
+           o=${d}/QAarchive.zip 
+       fi
+    else 
+       r=`echo $b | sed -e "s,/.*,,"` 
+       o=${store}/QAresults_${r}.root
+    fi
+    runs="$runs $r" 
+    mess "$i -> $o"
+    if test $noac -lt 1 && test ! -f $o ; then 
+       mess "alien_cp alien:${i} file:${o}"
+       alien_cp alien:${i} file:${o} > ${redir} 2>&1 
+    fi
+    if test $noac -lt 1 && test $arch -lt 1  ; then check_file $o ; fi
+    if test $noac -lt 1 && test $arch -gt 0 ; then 
+       (cd ${d} && unzip QAarchive.zip) > $redir 2>&1 
+    fi
+    let j=$j+1
+done 
+mess "Got a total of $j files for runs $runs"
+
+# --------------------------------------------------------------------
+#
+# EOF
+#
+
+    
\ No newline at end of file
diff --git a/PWG2/FORWARD/analysis2/scripts/ExtractData.C b/PWG2/FORWARD/analysis2/scripts/ExtractData.C
new file mode 100644 (file)
index 0000000..5cfd377
--- /dev/null
@@ -0,0 +1,370 @@
+// --- Get a single histogram ----------------------------------------
+TH1*
+GetOne(const TList* list, const char* which, bool mirror)
+{
+  if (!list) { 
+    Error("GetOne", "No list passed");
+    return 0;
+  }
+  TString n(Form("dndeta%s_rebin05", which));
+  if (mirror) n.Append("_mirror");
+  
+  TObject* o = list->FindObject(n);
+  if (!o) { 
+    Error("GetOne", "Object %s not found in %s", n.Data(), list->GetName());
+    return 0;
+  }
+  TH1* ret = static_cast<TH1*>(o);
+  ret->SetLineColor(ret->GetMarkerColor());
+  ret->SetDirectory(0);
+  return ret;
+}
+
+// --- Make point-to-point systematic errors -------------------------
+TH1*
+MakeSysError(TH1* h, Double_t sysErr)
+{
+  TString n(h->GetName());
+  n.Append("_syserr");
+  TH1* ret = static_cast<TH1*>(h->Clone(n));
+  ret->SetMarkerStyle(1);
+  ret->SetMarkerSize(0);
+  ret->SetMarkerColor(kBlue-10);
+  ret->SetFillColor(kBlue-10);
+  ret->SetFillStyle(1001);
+  ret->SetLineColor(kBlue-10);
+  ret->SetLineWidth(0);
+  ret->SetDirectory(0);
+  
+  for (Int_t i = 1; i <= ret->GetNbinsX(); i++) { 
+    Double_t c = ret->GetBinContent(i);
+    if (c < 0.001) { 
+      ret->SetBinContent(i,0);
+      ret->SetBinError(i,0);
+    }
+    Double_t e = c * sysErr/100;
+    ret->SetBinError(i,e);
+  }
+  
+  return ret;
+}
+
+// --- Turn a TGraphAsymmErrors into a histogram ---------------------
+TH1* Graph2Hist(const TGraphAsymmErrors* g)
+{
+  Int_t    nBins = g->GetN();
+  TArrayF  bins(nBins+1);
+  TArrayF  y(nBins);
+  TArrayF  ey(nBins);
+  Double_t dx = 0;
+  Double_t xmin = 10000;
+  Double_t xmax = -10000;
+  for (Int_t i = 0; i < nBins; i++) { 
+    Double_t x   = g->GetX()[i];
+    Double_t exl = g->GetEXlow()[i];
+    Double_t exh = g->GetEXhigh()[i];
+    xmin             = TMath::Min(x-exl, xmin);
+    xmax             = TMath::Max(x+exh, xmax);
+    bins.fArray[i]   = x-exl;
+    bins.fArray[i+1] = x+exh;
+    Double_t dxi = exh+exl;
+    if (dxi == 0 && i != 0) dxi = bins.fArray[i]-bins.fArray[i-1];
+    if (dx == 0) dx  = dxi;
+    else if (dxi != dx) dx = 0;
+    
+    y.fArray[i]  = g->GetY()[i];
+    ey.fArray[i] = TMath::Max(g->GetEYlow()[i],g->GetEYhigh()[i]);
+
+  }
+  TString name(g->GetName());
+  TString title(g->GetTitle());
+  TH1D* h = 0;
+  if (dx != 0) {
+    h = new TH1D(name.Data(), title.Data(), nBins, 
+                bins[0]-dx/2, bins[nBins]+dx/2);
+  }
+  else {
+    h = new TH1D(name.Data(), title.Data(), nBins, bins.fArray);
+  }
+  for (Int_t i = 1; i <= nBins; i++) { 
+    h->SetBinContent(i, y.fArray[i-1]);
+    h->SetBinError(i, ey.fArray[i-1]);
+  }
+  h->SetMarkerStyle(g->GetMarkerStyle());
+  h->SetMarkerColor(g->GetMarkerColor());
+  h->SetMarkerSize(g->GetMarkerSize());
+  h->SetDirectory(0);
+    
+  return h;
+}
+
+// --- Set Histogram properties --------------------------------------
+void SetAttributes(TH1* h, UShort_t sNN, Int_t which, Bool_t mirror)
+{
+  Int_t marker = (sNN == 900 ? 20     : 21) + (mirror ? 4 : 0);
+  Int_t color  = (which == 0 ? kRed+2  :
+                 which == 1 ? kMagenta+2 : 
+                 kBlue + 2);
+  h->SetMarkerColor(color);
+  h->SetLineColor(color);
+  h->SetMarkerStyle(marker);
+}
+
+  
+// --- Get publlished data via script --------------------------------
+TH1* GetPublished(UShort_t sNN, Bool_t isNSD)
+{
+  Long_t ptr = 0;
+  Int_t  typ = (isNSD ? 4 : 1);
+
+  ptr = gROOT->ProcessLine(Form("GetSingle(2,1,%d,%d)", sNN, typ));
+  if (!ptr) return 0;
+
+  TGraphAsymmErrors* g = reinterpret_cast<TGraphAsymmErrors*>(ptr);
+  TH1* h = Graph2Hist(g);
+  h->SetLineColor(h->GetMarkerColor());
+  
+  return h;
+}
+
+// --- Add points to stack -------------------------------------------
+Double_t
+AddToStack(THStack* stack, UShort_t sNN, Bool_t isNSD, 
+          TList* forward, TList* central, 
+          Double_t fwdSysErr, Double_t cenSysErr,
+          Double_t strangeCorr)
+{
+  TH1* fd1 = GetOne(forward, "Forward", false);
+  TH1* fd2 = GetOne(forward, "Forward", true);
+  fd1->Scale(1-strangeCorr/100);
+  fd2->Scale(1-strangeCorr/100);
+  TH1* fs1 = MakeSysError(fd1, fwdSysErr);
+  TH1* fs2 = MakeSysError(fd2, fwdSysErr);
+
+  TH1* cd  = 0;
+  TH1* cs  = 0;
+  if (central) { 
+    cd = GetOne(central, "Central", false);
+    cs = MakeSysError(cd, cenSysErr);
+  }
+  else {
+    cd = GetPublished(sNN, isNSD);
+  }
+  SetAttributes(fd1, sNN, 0, false);
+  SetAttributes(fd2, sNN, 0, true);
+  if (cd) SetAttributes(cd,  sNN, central ? 1 : 2, false);
+
+  if (cs) stack->Add(cs,  "e2");
+  stack->Add(fs1, "e2");
+  stack->Add(fs2, "e2");
+  if (cd) stack->Add(cd,  "ep");
+  stack->Add(fd1, "ep");
+  stack->Add(fd2, "ep");
+
+  Double_t mcd = (cd ? cd->GetMaximum() : 0);
+  Double_t mfs = fs1->GetMaximum();
+  
+  return TMath::Max(mcd, mfs);
+}
+
+// --- Find a list in directory --------------------------------------
+TList*
+GetList(const TDirectory* d, const char* what)
+{
+  if (!d) { 
+    Error("GetList", "No diretory passed");
+    return 0;
+  }
+  TList* p = static_cast<TList*>(d->Get(Form("%sResults", what)));
+  if (!p) { 
+    Error("GetList", "%sResults not found in %s", what, d->GetName());
+    return 0;
+  }
+  TList* r = static_cast<TList*>(p->FindObject("all"));
+  if (!r) { 
+    Error("GetList", "all not found in %s", p->GetName());
+    return 0;
+  }
+  return r;
+}
+
+void
+AdjustAxis(TAxis* a)
+{
+  a->SetTitleFont(132);
+  a->SetLabelFont(132);
+  a->SetTitleSize(0.08);
+  a->SetLabelSize(0.08);
+  a->SetTitleOffset(0.5);
+  a->SetNdivisions(10);
+}
+  
+// --- Make a stack for a single plot --------------------------------
+THStack*
+MakeStack(Bool_t isNSD,  Bool_t showClusters, 
+         Double_t strangeCorr, Double_t maxFactor=1.1)
+{
+  const char* trg = isNSD ? "nsd" : "inel";
+  TFile* f0900 =TFile::Open(Form("forward_dndeta_%s%04d.root",trg,900, "READ"));
+  TFile* f7000 =TFile::Open(Form("forward_dndeta_%s%04d.root",trg,7000,"READ"));
+  if (!f0900 || !f7000) { 
+    Error("MakeStack", "Failed to open one or more files (%p, %p)", 
+         f0900, f7000);
+    return 0;
+  }
+  TList* forward0900 = GetList(f0900, "Forward");
+  TList* forward7000 = GetList(f7000, "Forward");
+  TList* central0900 = 0;
+  TList* central7000 = showClusters ? GetList(f7000, "Central") : 0;
+
+  THStack* stack = new THStack("stack", "Stack");
+  Double_t sysDen = 5;
+  Double_t sysPt  = 2;
+  Double_t sysMix = 2;
+  Double_t sysNch = 5;
+  Double_t sysNor = 2;
+  Double_t fwdSys = TMath::Sqrt(sysDen * sysDen +
+                               sysPt  * sysPt  + 
+                               sysMix * sysMix + 
+                               sysNch * sysNch + 
+                               sysNor * sysNor);
+  Info("", "Forward systematic error: %4.1f", fwdSys);
+  Double_t m0900 = 
+    AddToStack(stack, 900,  isNSD, forward0900, central0900, 
+              fwdSys, 5, strangeCorr);
+  Double_t m7000 = 
+    AddToStack(stack, 7000, isNSD, forward7000, central7000, 
+              fwdSys, 5, strangeCorr);
+
+  stack->SetMaximum(maxFactor * TMath::Max(m0900, m7000));
+
+  f0900->Close();
+  f7000->Close();
+
+  return stack;
+}
+
+// --- Draw one stack ------------------------------------------------
+Double_t 
+DrawStack(Bool_t isNSD, Bool_t showClusters, 
+         Double_t strangeCorr, Double_t maxFactor=1.1)
+{
+  THStack* stack = MakeStack(isNSD, showClusters, strangeCorr, maxFactor);
+  stack->Draw("nostack ep");
+  stack->GetHistogram()->SetXTitle("#eta");
+  if (!isNSD) 
+    stack->GetHistogram()->SetYTitle("#frac{1}{N} #frac{dN_{ch}}{d#eta}");
+  if (!isNSD) 
+    stack->SetMinimum(.0001);
+  AdjustAxis(stack->GetHistogram()->GetXaxis());
+  AdjustAxis(stack->GetHistogram()->GetYaxis());
+  stack->GetHistogram()->GetXaxis()->SetTitleOffset(1);
+  gPad->Clear();
+  stack->Draw("nostack ep");
+
+  TLatex* title = new TLatex(1-gPad->GetRightMargin()-.01, 
+                            1-gPad->GetTopMargin()-.01, 
+                            (isNSD ? "NSD" : "INEL"));
+  title->SetNDC();
+  title->SetTextSize(0.1);
+  title->SetTextFont(132);
+  title->SetTextAlign(33);
+  title->SetTextColor(kBlue+2);
+  title->Draw();
+
+  return stack->GetMaximum();
+}
+
+// --- Draw one stack ------------------------------------------------
+void
+ExtractData(Bool_t showClusters = true)
+{
+  gROOT->LoadMacro("OtherData.C");
+  gStyle->SetOptTitle(0);
+  gStyle->SetGridColor(kGray);
+  TCanvas* c = new TCanvas("c", "C", 1200, 850);
+  c->SetRightMargin(0.01);
+  c->SetLeftMargin(0.1);
+  c->SetTopMargin(0.02);
+  c->SetBottomMargin(0.15);
+  c->SetFillColor(0);
+  c->SetBorderSize(0);
+  c->SetBorderMode(0);
+  c->cd();
+
+  c->Divide(1, 2, 0, 0);
+
+  TVirtualPad* p = c->cd(1);
+  p->SetFillColor(0);
+  p->SetRightMargin(0.02);
+  p->SetGridx();
+  p->SetGridy();
+  DrawStack(false, showClusters, 1.5);
+
+  Double_t ms = 1.2;
+
+  TLegend* l = new TLegend(.33, .01, .53, .35);
+  l->SetBorderSize(0);
+  l->SetFillColor(0);
+  l->SetTextFont(132);
+  l->SetFillStyle(0);
+  TLegendEntry* e = l->AddEntry("", "900GeV", "p");
+  e->SetMarkerStyle(20);
+  e->SetMarkerSize(ms+.1);
+  e = l->AddEntry("", "    7TeV", "p");
+  e->SetMarkerStyle(21);
+  e->SetMarkerSize(ms);
+  e = l->AddEntry("", "Mirrored data", "p");
+  e->SetMarkerStyle(24);
+  e->SetMarkerSize(ms);
+  l->Draw();
+
+  TLegend* l2 = new TLegend(.5, .01, .8, .35);
+  l2->SetBorderSize(0);
+  l2->SetFillColor(0);
+  l2->SetTextFont(132);
+  l2->SetFillStyle(0);
+  l2->SetColumnSeperation(-.05);
+  e = l2->AddEntry("", "Forward", "p");
+  e->SetMarkerStyle(20);
+  e->SetMarkerColor(kRed+2);
+  e->SetLineColor(kRed+2);
+  e->SetMarkerSize(ms);
+  if (showClusters) {
+    e = l2->AddEntry("", "Central", "p");
+    e->SetMarkerStyle(20);
+    e->SetMarkerColor(kMagenta+2);
+    e->SetLineColor(kMagenta+2);
+    e->SetMarkerSize(ms);
+  }
+  e = l2->AddEntry("", "#splitline{Eur.Phys.J.#font[22]{C68}:89-108}"
+                  "{Eur.Phys.J.#font[22]{C68}:345--354}", "p");
+  e->SetMarkerStyle(20);
+  e->SetMarkerColor(kBlue+2);
+  e->SetLineColor(kBlue+2);
+  e->SetMarkerSize(ms);
+  l2->Draw();
+
+
+  p = c->cd(2);
+  p->SetGridx();
+  p->SetGridy();
+  p->SetFillColor(0);
+  p->SetRightMargin(0.02);
+  DrawStack(true, showClusters, 1.5);
+
+  // TPad, x1, y1, x2, y2, ts, t1, t2, prel
+  gROOT->LoadMacro("AddLogo.C");
+  AddLogo((TPad*)p, .4, p->GetBottomMargin()+.05, 
+         .5, .44, 0.08, "", "pp data", true);
+  
+  c->cd();
+  TString out("dndeta_pp_forward");
+  if (!showClusters) out.Append("_noclusters");
+  c->SaveAs(Form("%s.png", out.Data()));
+  c->SaveAs(Form("%s.eps", out.Data()));
+}
+
+
+
+