]> git.uio.no Git - u/mrichter/AliRoot.git/blame - PWG0/highMultiplicity/AliHighMultiplicitySelector.cxx
warning fixes
[u/mrichter/AliRoot.git] / PWG0 / highMultiplicity / AliHighMultiplicitySelector.cxx
CommitLineData
9608df41 1/* $Id$ */
2
3#include "AliHighMultiplicitySelector.h"
4
5#include <TVector3.h>
6#include <TFile.h>
7#include <TH1F.h>
8#include <TH2F.h>
9#include <TNtuple.h>
10#include <TProfile.h>
11#include <TParticle.h>
12#include <TCanvas.h>
13#include <TTree.h>
14#include <TGeoManager.h>
15#include <TF1.h>
16#include <TGraph.h>
17#include <TLegend.h>
18#include <TLine.h>
dd367a14 19#include <TMath.h>
b3b260d1 20#include <TLegend.h>
21#include <TText.h>
9608df41 22
23#include <AliLog.h>
24#include <AliESD.h>
25#include <AliRunLoader.h>
26#include <AliStack.h>
27
28#include <AliITSgeom.h>
29#include <AliITSLoader.h>
30#include <AliITSdigitSPD.h>
31#include <AliITSRecPoint.h>
32
33#include "AliPWG0Helper.h"
34
35//
a9aed06c 36// Selector that produces plots needed for the high multiplicity analysis with the
37// pixel detector
38// Needs cluster file
9608df41 39//
40
41ClassImp(AliHighMultiplicitySelector)
42
43AliHighMultiplicitySelector::AliHighMultiplicitySelector() :
44 AliSelectorRL(),
45 fChipsLayer1(0),
46 fChipsLayer2(0),
47 fL1vsL2(0),
48 fMvsL1(0),
49 fMvsL2(0),
50 fChipsFired(0),
51 fPrimaryL1(0),
52 fPrimaryL2(0),
53 fClusterZL1(0),
54 fClusterZL2(0),
55 fClvsL1(0),
56 fClvsL2(0),
a9aed06c 57 fCentralRegion(kFALSE)
9608df41 58{
59 //
60 // Constructor. Initialization of pointers
61 //
62}
63
64AliHighMultiplicitySelector::~AliHighMultiplicitySelector()
65{
66 //
67 // Destructor
68 //
69
70 // histograms are in the output list and deleted when the output
71 // list is deleted by the TSelector dtor
72}
73
74void AliHighMultiplicitySelector::SlaveBegin(TTree *tree)
75{
a9aed06c 76 // create histograms
77
9608df41 78 AliSelectorRL::SlaveBegin(tree);
79
80 fChipsFired = new TH2F("fChipsFired", ";Module;Chip;Count", 240, -0.5, 239.5, 5, -0.5, 4.5);
81
82 fPrimaryL1 = new TNtuple("fPrimaryL1", "", "multiplicity:firedChips:chipsByPrimaries:clusters");
83 fPrimaryL2 = new TNtuple("fPrimaryL2", "", "multiplicity:firedChips:chipsByPrimaries:clusters");
84
85 fClusterZL1 = new TH1F("fClusterZL1", ";z", 400, -20, 20);
86 fClusterZL2 = new TH1F("fClusterZL2", ";z", 400, -20, 20);
87}
88
89void AliHighMultiplicitySelector::Init(TTree* tree)
90{
91 // read the user objects
92
93 AliSelectorRL::Init(tree);
94
95 // enable only the needed branches
96 if (tree)
97 {
98 tree->SetBranchStatus("*", 0);
99 tree->SetBranchStatus("fTriggerMask", 1);
100
101 /*if (fTree->GetCurrentFile())
102 {
103 TString fileName(fTree->GetCurrentFile()->GetName());
104 fileName.ReplaceAll("AliESDs", "geometry");
105
106 // load geometry
107 TGeoManager::Import(fileName);
108 }*/
109 }
110}
111
112Bool_t AliHighMultiplicitySelector::Process(Long64_t entry)
113{
114 //
115 // processing
116 //
117
118 if (AliSelectorRL::Process(entry) == kFALSE)
119 return kFALSE;
120
121 // Check prerequisites
122 if (!fESD)
123 {
124 AliDebug(AliLog::kError, "ESD branch not available");
125 return kFALSE;
126 }
127
70fdd197 128 static AliTriggerAnalysis* triggerAnalysis = new AliTriggerAnalysis;
129 Bool_t eventTriggered = triggerAnalysis->IsTriggerBitFired(fESD->GetTriggerMask(), AliTriggerAnalysis::kMB1);
9608df41 130
131 if (!eventTriggered)
132 {
133 AliDebug(AliLog::kDebug, "Event not triggered. Skipping.");
134 return kTRUE;
135 }
136
137 AliStack* stack = GetStack();
138 if (!stack)
139 {
140 AliDebug(AliLog::kError, "Stack not available");
141 return kFALSE;
142 }
143
144 Int_t nPrim = stack->GetNprimary();
145 Int_t multiplicity21 = 0;
146 Int_t multiplicity16 = 0;
147
148 for (Int_t iMc = 0; iMc < nPrim; ++iMc)
149 {
150 AliDebug(AliLog::kDebug+1, Form("MC Loop: Processing particle %d.", iMc));
151
152 TParticle* particle = stack->Particle(iMc);
153
154 if (!particle)
155 {
156 AliDebug(AliLog::kError, Form("UNEXPECTED: particle with label %d not found in stack (mc loop).", iMc));
157 continue;
158 }
159
160 if (AliPWG0Helper::IsPrimaryCharged(particle, nPrim) == kFALSE)
161 continue;
162
a9aed06c 163 if (fCentralRegion)
9608df41 164 {
165 if (TMath::Abs(particle->Eta()) < 1.05)
166 multiplicity21++;
167 if (TMath::Abs(particle->Eta()) < 0.8)
168 multiplicity16++;
169 }
170 else
171 {
172 if (TMath::Abs(particle->Eta()) < 2.1)
173 multiplicity21++;
174 if (TMath::Abs(particle->Eta()) < 1.6)
175 multiplicity16++;
176 }
177 }// end of mc particle
178
179 AliRunLoader* runLoader = GetRunLoader();
180 if (!runLoader)
181 {
182 AliDebug(AliLog::kError, "runloader not available");
183 return kFALSE;
184 }
185
186 // TDirectory::TContext restores the current directory is restored when the scope ends.
187 // This helps around ROOT bug #26025 and is good behaviour anyway
188 TDirectory::TContext context(0);
189 AliITSLoader* loader = (AliITSLoader*) runLoader->GetLoader( "ITSLoader" );
190 loader->LoadDigits("READ");
191 TTree* treeD = loader->TreeD();
192 if (!treeD)
193 {
194 AliDebug(AliLog::kError, "Could not retrieve TreeD of ITS");
195 return kFALSE;
196 }
197
198 treeD->SetBranchStatus("*", 0);
199 treeD->SetBranchStatus("ITSDigitsSPD.fTracks*", 1);
200 treeD->SetBranchStatus("ITSDigitsSPD.fCoord1", 1);
201
202 TClonesArray* digits = 0;
203 treeD->SetBranchAddress("ITSDigitsSPD", &digits);
a6e0ebfe 204 if (digits)
9608df41 205 digits->Clear();
206
207 // each value for both layers
208 Int_t totalNumberOfFO[2];
209 Int_t chipsHitByPrimaries[2];
210 //Int_t chipsHitBySecondaries[2];
211
212 for (Int_t i=0; i<2; ++i)
213 {
214 totalNumberOfFO[i] = 0;
215 chipsHitByPrimaries[i] = 0;
216 //chipsHitBySecondaries[i] = 0;
217 }
218
219 Int_t startSPD = 0; //geom->GetStartSPD();
220 Int_t lastSPD = 239; //geom->GetLastSPD();
221
222 //printf("%d %d\n", startSPD, lastSPD);
223// for (Int_t l=0; l<240; ++l) { AliITSgeomTGeo::GetModuleId(l, i, j, k); printf("%d --> %d\n", l, i); }
224
225 // loop over modules (ladders)
226 for (Int_t moduleIndex=startSPD; moduleIndex<lastSPD+1; moduleIndex++)
227 {
a9aed06c 228 if (fCentralRegion)
9608df41 229 {
230 if ((moduleIndex % 4) == 0 || (moduleIndex % 4) == 3)
231 continue;
232 }
233
234 Int_t currentLayer = 0;
235 if (moduleIndex >= 80)
236 currentLayer = 1;
237
238 treeD->GetEvent(moduleIndex);
239
240 // get number of digits in this module
241 Int_t ndigitsInModule = digits->GetEntriesFast();
242
243 // get number of digits in each chip of the module
244 Int_t ndigitsInChip[5];
245 Bool_t hitByPrimary[5];
246 for( Int_t iChip=0; iChip<5; iChip++)
247 {
248 ndigitsInChip[iChip]=0;
249 hitByPrimary[iChip] = kFALSE;
250 }
251
252 // loop over digits in this module
253 for (Int_t iDig=0; iDig<ndigitsInModule; iDig++)
254 {
255 AliITSdigitSPD* dp = (AliITSdigitSPD*) digits->At(iDig);
256 Int_t column = dp->GetCoord1();
257 Int_t isChip = column / 32;
258
259 //printf("Digit %d has column %d which translates to chip %d\n", iDig, column, isChip);
260
261 fChipsFired->Fill(moduleIndex, isChip);
262
263 ndigitsInChip[isChip]++;
264
265 Bool_t debug = kFALSE;
266
267 // find out which particle caused this chip to fire
268 // if we find at least one primary we consider this chip being fired by a primary
269 for (Int_t track=0; track<10; ++track)
270 {
271 Int_t label = dp->GetTrack(track);
272
273 if (label < 0)
274 continue;
275
276 if (debug)
277 printf("track %d contains label %d\n", track, label);
278
279 TParticle* particle = stack->Particle(label);
280
281 if (!particle)
282 {
283 AliDebug(AliLog::kError, Form("UNEXPECTED: particle with label %d not found in stack (digit loop).", label));
284 continue;
285 }
286
287 if (debug)
288 {
289 particle->Print();
290 printf("statuscode = %d, p = %f, m = %d\n", particle->GetStatusCode(), particle->P(), particle->GetFirstMother());
291 }
292
293 // TODO delta electrons should be traced back to their mother. this is e.g. solved in AliITSClusterFinderV2::CheckLabels2
294 while (particle->P() < 0.02 && particle->GetStatusCode() == 0 && particle->GetFirstMother() >= 0)
295 {
296 label = particle->GetFirstMother();
297 particle = stack->Particle(label);
298
299 if (!particle)
300 break;
301
302 if (debug)
303 {
304 printf("-->\n");
305 printf("statuscode = %d, p = %f, m = %d\n", particle->GetStatusCode(), particle->P(), particle->GetFirstMother());
306 particle->Print();
307 }
308 }
309
310 if (!particle)
311 {
312 AliDebug(AliLog::kError, Form("UNEXPECTED: particle with label %d not found in stack (digit loop, finding delta electrons).", label));
313 continue;
314 }
315
316 if (label > nPrim)
317 continue;
318
319 if (AliPWG0Helper::IsPrimaryCharged(particle, nPrim) == kFALSE)
320 continue;
321
322 if (debug)
323 printf("This was a primary (or delta-electron of a primary)!\n");
324
325 hitByPrimary[isChip] = kTRUE;
326 }
327 }
328
329 // get number of FOs in the module
330 for (Int_t ifChip=0; ifChip<5; ifChip++)
331 if( ndigitsInChip[ifChip] >= 1 )
332 {
333 totalNumberOfFO[currentLayer]++;
334 if (hitByPrimary[ifChip])
335 {
336 chipsHitByPrimaries[currentLayer]++;
337 }
338 //else
339 // chipsHitBySecondaries[currentLayer]++;
340 }
341 }
342
343 //printf("Fired chips: %d %d\n", totalNumberOfFOLayer1, totalNumberOfFOLayer2);
344
345 // now find clusters
346 Int_t clustersLayer[2];
347 clustersLayer[0] = 0;
348 clustersLayer[1] = 0;
349
350 loader->LoadRecPoints("READ");
351 TTree* treeR = loader->TreeR();
352 if (!treeR)
353 {
354 AliDebug(AliLog::kError, "Could not retrieve TreeR of ITS");
355 return kFALSE;
356 }
357
358 // TODO branches!
359 //treeR->SetBranchStatus("*", 0);
360
361 TClonesArray* itsClusters = 0;
362 treeR->SetBranchAddress("ITSRecPoints", &itsClusters);
363
364 Int_t nTreeEntries = treeR->GetEntries();
365 for (Int_t iEntry = 0; iEntry < nTreeEntries; ++iEntry)
366 {
367 if (!treeR->GetEvent(iEntry))
368 continue;
369
370 Int_t nClusters = itsClusters->GetEntriesFast();
371
372 while(nClusters--)
373 {
374 AliITSRecPoint* cluster = (AliITSRecPoint*) itsClusters->UncheckedAt(nClusters);
375
376 if (cluster->GetLayer() == 0)
377 {
378 clustersLayer[0]++;
379 fClusterZL1->Fill(cluster->GetZ());
380 }
381 else if (cluster->GetLayer() == 1)
382 {
383 clustersLayer[1]++;
384 fClusterZL2->Fill(cluster->GetZ());
385 }
386 }
387 }
388
389 fPrimaryL1->Fill(multiplicity21, totalNumberOfFO[0], chipsHitByPrimaries[0], clustersLayer[0]);
390 fPrimaryL2->Fill(multiplicity16, totalNumberOfFO[1], chipsHitByPrimaries[1], clustersLayer[1]);
391
392 return kTRUE;
393}
394
395Bool_t AliHighMultiplicitySelector::Notify()
396{
a9aed06c 397 // get next ITS runloader
398
9608df41 399 AliRunLoader* runLoader = GetRunLoader();
400
401 if (runLoader)
402 {
403 AliITSLoader* loader = (AliITSLoader* )runLoader->GetLoader( "ITSLoader" );
404 if (loader)
405 {
406 loader->UnloadDigits();
407 loader->UnloadRecPoints();
408 }
409 }
410
411 return AliSelectorRL::Notify();
412}
413
414void AliHighMultiplicitySelector::SlaveTerminate()
415{
416 // The SlaveTerminate() function is called after all entries or objects
417 // have been processed. When running with PROOF SlaveTerminate() is called
418 // on each slave server.
419
420 AliSelectorRL::SlaveTerminate();
421
422 // Add the histograms to the output on each slave server
423 if (!fOutput)
424 {
425 AliDebug(AliLog::kError, "ERROR: Output list not initialized.");
426 return;
427 }
428
429 fOutput->Add(fChipsFired);
430 fOutput->Add(fPrimaryL1);
431 fOutput->Add(fPrimaryL2);
432 fOutput->Add(fClusterZL1);
433 fOutput->Add(fClusterZL2);
434}
435
436void AliHighMultiplicitySelector::Terminate()
437{
438 // The Terminate() function is the last function to be called during
439 // a query. It always runs on the client, it can be used to present
440 // the results graphically or save the results to file.
441
442 AliSelectorRL::Terminate();
443
444 fChipsFired = dynamic_cast<TH2F*> (fOutput->FindObject("fChipsFired"));
445 fPrimaryL1 = dynamic_cast<TNtuple*> (fOutput->FindObject("fPrimaryL1"));
446 fPrimaryL2 = dynamic_cast<TNtuple*> (fOutput->FindObject("fPrimaryL2"));
447 fClusterZL1 = dynamic_cast<TH1F*> (fOutput->FindObject("fClusterZL1"));
448 fClusterZL2 = dynamic_cast<TH1F*> (fOutput->FindObject("fClusterZL2"));
449
450 if (!fClusterZL1 || !fClusterZL2 || !fChipsFired || !fPrimaryL1 || !fPrimaryL2)
451 {
452 AliError("Histograms not available");
453 return;
454 }
455
456 WriteHistograms();
457}
458
459void AliHighMultiplicitySelector::WriteHistograms(const char* filename)
460{
a9aed06c 461 // write the histograms to a file
462
9608df41 463 TFile* file = TFile::Open(filename, "RECREATE");
464
465 fChipsFired->Write();
466 fPrimaryL1->Write();
467 fPrimaryL2->Write();
468 fClusterZL1->Write();
469 fClusterZL2->Write();
470
471 file->Close();
472}
473
474void AliHighMultiplicitySelector::ReadHistograms(const char* filename)
475{
a9aed06c 476 // read the data from a file and fill histograms
477
9608df41 478 TFile* file = TFile::Open(filename);
479
480 if (!file)
481 return;
482
483 fPrimaryL1 = dynamic_cast<TNtuple*> (file->Get("fPrimaryL1"));
484 fPrimaryL2 = dynamic_cast<TNtuple*> (file->Get("fPrimaryL2"));
485 fChipsFired = dynamic_cast<TH2F*> (file->Get("fChipsFired"));
486 fClusterZL1 = dynamic_cast<TH1F*> (file->Get("fClusterZL1"));
487 fClusterZL2 = dynamic_cast<TH1F*> (file->Get("fClusterZL2"));
335a5e1b 488
489 if (!fPrimaryL1 || !fPrimaryL2 || !fChipsFired || !fClusterZL1 || !fClusterZL2)
490 return;
9608df41 491
492 #define MULT 1001, -0.5, 1000.5
493 #define BINNING_LAYER1 401, -0.5, 400.5
494 #define BINNING_LAYER2 801, -0.5, 800.5
495
496 fChipsLayer1 = new TH1F("fChipsLayer1", "Layer 1;Fired Chips;Count", BINNING_LAYER1);
497 fChipsLayer2 = new TH1F("fChipsLayer2", "Layer 2;Fired Chips;Count", BINNING_LAYER2);
498
499 fL1vsL2 = new TH2F("fL1vsL2", ";Fired Chips Layer 1;Fired Chips Layer 2", BINNING_LAYER1, BINNING_LAYER2);
500 fMvsL1 = new TH2F("fMvsL1", ";true multiplicity;fired chips layer1", MULT, BINNING_LAYER1);
501 fMvsL2 = new TH2F("fMvsL2", ";true multiplicity;fired chips layer2", MULT, BINNING_LAYER2);
502
503 fClvsL1 = new TH2F("fClvsL1", ";clusters layer1;fired chips layer1", MULT, BINNING_LAYER1);
504 fClvsL2 = new TH2F("fClvsL2", ";clusters layer2;fired chips layer2", MULT, BINNING_LAYER2);
505
506 for (Int_t i = 0; i < fPrimaryL1->GetEntries(); i++)
507 {
508 fPrimaryL1->GetEvent(i);
509 fPrimaryL2->GetEvent(i);
510
511 Int_t multiplicity21 = (Int_t) fPrimaryL1->GetArgs()[0];
512 Int_t multiplicity16 = (Int_t) fPrimaryL2->GetArgs()[0];
513
514 Int_t totalNumberOfFO[2];
515 totalNumberOfFO[0] = (Int_t) fPrimaryL1->GetArgs()[1];
516 totalNumberOfFO[1] = (Int_t) fPrimaryL2->GetArgs()[1];
517
518 Int_t chipsHitByPrimaries[2];
519 chipsHitByPrimaries[0] = (Int_t) fPrimaryL1->GetArgs()[2];
520 chipsHitByPrimaries[1] = (Int_t) fPrimaryL2->GetArgs()[2];
521
522 Int_t clustersLayer[2];
523 clustersLayer[0] = (Int_t) fPrimaryL1->GetArgs()[3];
524 clustersLayer[1] = (Int_t) fPrimaryL2->GetArgs()[3];
525
526 fChipsLayer1->Fill(totalNumberOfFO[0]);
527 fChipsLayer2->Fill(totalNumberOfFO[1]);
528
529 fL1vsL2->Fill(totalNumberOfFO[0], totalNumberOfFO[1]);
530
531 fMvsL1->Fill(multiplicity21, totalNumberOfFO[0]);
532 fMvsL2->Fill(multiplicity16, totalNumberOfFO[1]);
533
534 fClvsL1->Fill(clustersLayer[0], totalNumberOfFO[0]);
535 fClvsL2->Fill(clustersLayer[1], totalNumberOfFO[1]);
536 }
537}
538
b3b260d1 539TH1* AliHighMultiplicitySelector::GetTriggerEfficiency(TH2* multVsLayer, Int_t cut, Int_t upperCut)
9608df41 540{
f6093269 541 //
542 // returns the trigger efficiency as function of multiplicity with a given cut
543 //
9608df41 544
545 //cut and multiply with x-section
f6093269 546 TH1* allEvents = multVsLayer->ProjectionX("fMvsL_x_total", 1, 1001);
9608df41 547 //allEvents->Sumw2();
548
549 //cut and multiply with x-section
b3b260d1 550 TH1* proj = multVsLayer->ProjectionX(Form("%s_x", multVsLayer->GetName()), cut, upperCut);
9608df41 551 //proj->Sumw2();
552
f6093269 553 //new TCanvas; allEvents->DrawCopy(); gPad->SetLogy();
554 //new TCanvas; proj->DrawCopy(); gPad->SetLogy();
9608df41 555
556 // make probability distribution out of it
557 // TODO binomial errors do not work??? weird...
558 proj->Divide(proj, allEvents, 1, 1, "B");
559
f6093269 560 return proj;
561}
562
563TH1* AliHighMultiplicitySelector::GetXSectionCut(TH1* xSection, TH2* multVsLayer, Int_t cut)
564{
565 // returns the rel. cross section of the true spectrum that is measured when a cut at <cut> is performed
566
567 TH1* proj = GetTriggerEfficiency(multVsLayer, cut);
568
569 //new TCanvas; proj->DrawCopy(); gPad->SetLogy();
9608df41 570
571 for (Int_t i=1; i<=proj->GetNbinsX(); i++)
572 {
573 if (i <= xSection->GetNbinsX())
574 {
575 Double_t value = proj->GetBinContent(i) * xSection->GetBinContent(i);
576 Double_t error = 0;
577
578 if (value != 0)
579 error = value * (proj->GetBinError(i) / proj->GetBinContent(i) + xSection->GetBinError(i) / xSection->GetBinContent(i));
580
581 proj->SetBinContent(i, value);
582 proj->SetBinError(i, error);
583 }
584 else
585 {
586 proj->SetBinContent(i, 0);
587 proj->SetBinError(i, 0);
588 }
589 }
590
f6093269 591 //new TCanvas; proj->DrawCopy(); gPad->SetLogy();
9608df41 592
593 return proj;
594}
595
f6093269 596void AliHighMultiplicitySelector::MakeGraphs2(const char* title, TH1* xSection, TH2* fMvsL)
9608df41 597{
a9aed06c 598 // creates graphs
599
f6093269 600 TGraph* effGraph = new TGraph;
601 effGraph->SetTitle(Form("%s;Cut on fired chips;mult. where eff. >50%%", title));
602 TGraph* ratioGraph = new TGraph;
603 ratioGraph->SetTitle(Form("%s;Cut on fired chips;x-section_(>=eff. limit) / x-section_(total)", title));
604 TGraph* totalGraph = new TGraph;
605 totalGraph->SetTitle(Form("%s;Cut on fired chips;rel x-section_(>=eff. limit)", title));
606
607 for (Int_t cut = 0; cut <= 300; cut+=50)
608 {
609 TH1* proj = (TH1*) GetTriggerEfficiency(fMvsL, cut)->Clone("clone");
610
611 //proj->Rebin(3);
612 //proj->Scale(1.0 / 3);
613
614 new TCanvas; proj->DrawCopy();
9608df41 615
f6093269 616 Int_t limitBin = proj->GetNbinsX()+1;
617 while (limitBin > 1 && proj->GetBinContent(limitBin-1) > 0.5)
618 limitBin--;
619
620 Float_t limit = proj->GetXaxis()->GetBinCenter(limitBin);
621
622 effGraph->SetPoint(effGraph->GetN(), cut, limit);
623
624 proj = GetXSectionCut(xSection, fMvsL, cut);
625
626 Double_t ratio = 0;
627 Double_t total = 0;
628 if (proj->Integral(1, 1001) > 0)
629 {
630 ratio = proj->Integral(proj->FindBin(limit), 1001) / proj->Integral(1, 1001);
631 total = proj->Integral(proj->FindBin(limit), 1001);
632 }
633
634 ratioGraph->SetPoint(ratioGraph->GetN(), cut, ratio);
635 totalGraph->SetPoint(totalGraph->GetN(), cut, total);
636
637 Printf("Cut at %d --> trigger eff. is > 0.5 for mult. >= %.2f. That is the case for %f of the triggered, %e of all events", cut, limit, ratio, total);
638 }
639
640 TCanvas* canvas = new TCanvas(Form("%s_Efficiency", title), Form("%s_Efficiency", title), 1200, 800);
641 canvas->Divide(2, 2);
642
643 canvas->cd(1);
644 effGraph->Draw("A*");
645
646 for (Int_t i=8; i<=10; ++i)
647 {
648 TLine* line = new TLine(0, xSection->GetMean() * i, 300, xSection->GetMean() * i);
649 line->Draw();
650 }
651
652 canvas->cd(2); ratioGraph->Draw("A*");
653 canvas->cd(3); gPad->SetLogy(); totalGraph->Draw("A*");
654
655 canvas->SaveAs(Form("%s.gif", canvas->GetName()));
656}
657
658void AliHighMultiplicitySelector::MakeGraphs(const char* title, TH1* xSection, TH2* fMvsL, Int_t limit)
659{
9608df41 660 // relative x-section, once we have a collision
a9aed06c 661
9608df41 662 xSection->Scale(1.0 / xSection->Integral());
663
664 TGraph* ratioGraph = new TGraph;
665 ratioGraph->SetTitle(Form("%s;Cut on fired chips;x-section_(>=%d) / x-section_(total)", title, limit));
666 TGraph* totalGraph = new TGraph;
667 totalGraph->SetTitle(Form("%s;Cut on fired chips;rel x-section_(>=%d)", title, limit));
668
669 Double_t max = 0;
670 Int_t bestCut = -1;
671 Double_t bestRatio = -1;
672 Double_t bestTotal = -1;
673 Int_t fullCut = -1;
674 Double_t fullRatio = -1;
675 Double_t fullTotal = -1;
676
677 fMvsL->Sumw2();
678
679 for (Int_t cut = 50; cut <= 300; cut+=2)
680 {
681 TH1* proj = GetXSectionCut(xSection, fMvsL, cut);
682
683 Double_t ratio = 0;
684 Double_t total = 0;
685 if (proj->Integral(1, 1000) > 0)
686 {
687 ratio = proj->Integral(limit, 1000) / proj->Integral(1, 1000);
688 total = proj->Integral(limit, 1000);
689 }
690
691 max = TMath::Max(max, total);
692
693 //printf("Cut at %d: rel. x-section_(>=%d) = %e; x-section_(>=%d) / x-section_(total) = %f\n", cut, limit, total, limit, ratio);
694
695 if (total < max * 0.9 && bestCut == -1)
696 {
697 bestCut = cut;
698 bestRatio = ratio;
699 bestTotal = total;
700 }
701
702 if (ratio == 1 && fullCut == -1)
703 {
704 fullCut = cut;
705 fullRatio = ratio;
706 fullTotal = total;
707 }
708
709 ratioGraph->SetPoint(ratioGraph->GetN(), cut, ratio);
710 totalGraph->SetPoint(totalGraph->GetN(), cut, total);
711 }
712
713 if (bestCut != -1)
714 printf("Best cut at %d: rel. x-section_(>=%d) = %e %%; x-section_(>=%d) / x-section_(total) = %f %%\n", bestCut, limit, bestTotal, limit, bestRatio);
715 if (fullCut != -1)
716 printf("100%% cut at %d: rel. x-section_(>=%d) = %e %%; x-section_(>=%d) / x-section_(total) = %f %%\n", fullCut, limit, fullTotal, limit, fullRatio);
717
718 TCanvas* canvas = new TCanvas(Form("%s_RatioXSection_%d", title, limit), Form("%s_RatioXSection_%d", title, limit), 600, 400);
719 ratioGraph->Draw("A*");
720 canvas->SaveAs(Form("%s.gif", canvas->GetName()));
721
722 canvas = new TCanvas(Form("%s_TotalXSection_%d", title, limit), Form("%s_TotalXSection_%d", title, limit), 600, 400);
723 totalGraph->Draw("A*");
724 canvas->SaveAs(Form("%s.gif", canvas->GetName()));
725}
726
727void AliHighMultiplicitySelector::JPRPlots()
728{
a9aed06c 729 // more plots
730
9608df41 731 /*
732
733 gSystem->Load("libPWG0base");
734 .L AliHighMultiplicitySelector.cxx+
735 x = new AliHighMultiplicitySelector();
736 x->ReadHistograms("highmult_hijing100k.root");
737 x->JPRPlots();
738
739 */
740
741 // get x-sections
742 TFile* file = TFile::Open("crosssectionEx.root");
743 if (!file)
744 return;
745
746 TH1* xSections[2];
747 xSections[0] = dynamic_cast<TH1*> (gFile->Get("xSection2Ex"));
748 xSections[1] = dynamic_cast<TH1*> (gFile->Get("xSection15Ex"));
749
750 for (Int_t i=0; i<2; ++i)
751 {
752 if (!xSections[i])
753 continue;
754
755 TH1* xSection = xSections[i];
756 TH2* fMvsL = (i == 0) ? fMvsL1: fMvsL2;
757 //Int_t cut = (i == 0) ? 164 : 150; // 8 times the mean
758 //Int_t cut = (i == 0) ? 178 : 166; // 9 times the mean
759 Int_t cut = (i == 0) ? 190 : 182; // 10 times the mean
760
f6093269 761 // limit is N times the mean
762 Int_t limit = (Int_t) (xSection->GetMean() * 10);
763
764 // 10^28 lum --> 1.2 kHz
765 // 10^31 lum --> 1200 kHz
766 Float_t rate = 1200e3;
767
768 // time in s
769 Float_t lengthRun = 1e6;
770
9608df41 771 xSection->SetStats(kFALSE);
f6093269 772 xSection->SetTitle(""); //(i == 0) ? "SPD Layer 1" : "SPD Layer 2");
9608df41 773 xSection->GetXaxis()->SetTitle(Form("true multiplicity in |#eta| < %.1f", (i == 0) ? 2.0 : 1.5));
774 xSection->GetXaxis()->SetRangeUser(0, (i == 0) ? 400 : 350);
f6093269 775 //xSection->GetYaxis()->SetTitle("relative cross section");
9608df41 776 xSection->GetYaxis()->SetTitleOffset(1.2);
777
9608df41 778 // relative x-section, once we have a collision
779 xSection->Scale(1.0 / xSection->Integral());
780
781 TH1* proj = GetXSectionCut(xSection, fMvsL, cut);
782
783 Double_t ratio = 0;
784 Double_t total = 0;
785 if (proj->Integral(1, 1000) > 0)
786 {
787 ratio = proj->Integral(limit, 1000) / proj->Integral(1, 1000);
788 total = proj->Integral(limit, 1000);
789 }
790
791 printf("Cut at %d: rel. x-section_(>=%d) = %e; x-section_(>=%d) / x-section_(total) = %f\n", cut, limit, total, limit, ratio);
792
793 TCanvas* canvas = new TCanvas(Form("HMPlots_%d", i), Form("HMPlots_%d", i), 800, 600);
794 canvas->SetLogy();
795 xSection->DrawCopy();
796 proj->SetLineColor(2);
797 proj->SetStats(kFALSE);
798 proj->DrawCopy("SAME");
799
800 TLegend* legend = new TLegend(0.15, 0.15, 0.45, 0.3);
801 legend->SetFillColor(0);
802 legend->AddEntry(xSection, "no trigger");
803 legend->AddEntry(proj, Form("FO trigger > %d chips", cut));
804 legend->Draw();
805
806 TLine* line = new TLine(limit, xSection->GetMinimum() * 0.5, limit, xSection->GetMaximum() * 2);
807 line->SetLineWidth(2);
808 line->Draw();
809
810 canvas->SaveAs(Form("%s.gif", canvas->GetName()));
811
812 TCanvas* canvas2 = new TCanvas(Form("HMPlots_%d_Random", i), Form("HMPlots_%d_Random", i), 800, 600);
f6093269 813 //canvas2->SetTopMargin(0.05);
814 //canvas2->SetRightMargin(0.05);
9608df41 815 canvas2->SetLogy();
f6093269 816 xSection->DrawCopy("HIST");
9608df41 817
f6093269 818 TLegend* legend2 = new TLegend(0.15, 0.15, 0.6, 0.3);
9608df41 819 legend2->SetFillColor(0);
820 legend2->AddEntry(xSection, "no trigger");
821
822 TH1* proj2 = (TH1*) proj->Clone("random");
823 proj2->Reset();
f6093269 824 // MB lengthRun s 100 Hz
825 Int_t nTrigger = (Int_t) (100 * lengthRun * proj->Integral(1, 1000));
9608df41 826 proj2->FillRandom(proj, nTrigger);
827
828 TH1* proj3 = (TH1*) proj2->Clone("random_clone");
829 proj3->Divide(proj);
830 proj3->Fit("pol0", "0", "");
831 proj2->Scale(1.0 / proj3->GetFunction("pol0")->GetParameter(0));
832
f6093269 833 /*
9608df41 834 proj2->DrawCopy("SAME");
835 legend2->AddEntry(proj2, Form("%d evts, FO > %d chips (%d evts)", nTrigger, cut, (Int_t) (nTrigger * ratio)));
f6093269 836 */
9608df41 837
838 proj2 = (TH1*) proj->Clone("random2");
839 proj2->Reset();
f6093269 840 // 10^31 lum --> 1200 kHz; lengthRun s
841 nTrigger = (Int_t) (rate * proj->Integral(1, 1000) * lengthRun);
9608df41 842 proj2->FillRandom(proj, nTrigger);
843
844 proj3 = (TH1*) proj2->Clone("random_clone2");
845 proj3->Divide(proj);
846 proj3->Fit("pol0", "0", "");
847 proj2->Scale(1.0 / proj3->GetFunction("pol0")->GetParameter(0));
848
849 proj2->SetLineColor(4);
f6093269 850 proj2->SetMarkerStyle(7);
851 proj2->SetMarkerColor(4);
852 proj2->DrawCopy("SAME P");
853 //legend2->AddEntry(proj2, Form("%d evts, FO > %d chips (%d evts)", nTrigger, cut, (Int_t) (nTrigger * ratio)));
854 legend2->AddEntry(proj2, Form("FO trigger > %d chips", cut));
9608df41 855
856 legend2->Draw();
857 line->Draw();
858
859 canvas2->SaveAs(Form("%s.gif", canvas2->GetName()));
f6093269 860 canvas2->SaveAs(Form("%s.eps", canvas2->GetName()));
9608df41 861 }
862}
863
d1594f8a 864void AliHighMultiplicitySelector::Ntrigger(Bool_t relative)
f91bc12d 865{
866 //
867 // produces a spectrum created with N triggers
868 // number of triggers and thresholds for the moment fixed
869 //
870
871 /*
872
dd367a14 873 gSystem->Load("libANALYSIS");
f91bc12d 874 gSystem->Load("libPWG0base");
875 .L AliHighMultiplicitySelector.cxx+g
876 x = new AliHighMultiplicitySelector();
877 x->ReadHistograms("highmult_hijing100k.root");
878 x->Ntrigger();
879
d1594f8a 880 gSystem->Load("libPWG0base");
881 .L AliHighMultiplicitySelector.cxx+g
882 x = new AliHighMultiplicitySelector();
883 x->ReadHistograms("highmult_hijing100k.root");
884 x->Ntrigger(kFALSE);
885
f91bc12d 886 */
887
888 // get x-sections
889 TFile* file = TFile::Open("crosssectionEx.root");
890 if (!file)
891 return;
892
893 TH1* xSections[2];
894 xSections[0] = dynamic_cast<TH1*> (gFile->Get("xSection2Ex"));
895 xSections[1] = dynamic_cast<TH1*> (gFile->Get("xSection15Ex"));
896
51f6de65 897 // 10^28 lum --> 1.4 kHz
898 // 10^31 lum --> 1400 kHz
899 //Float_t rate = 1400e3;
900 Float_t rate = 1.4e3;
f91bc12d 901
902 // time in s
51f6de65 903 Float_t lengthRun = 1e5;
f91bc12d 904
905 Int_t colors[] = { 2, 3, 4, 6, 7, 8 };
906 Int_t markers[] = { 7, 2, 4, 5, 6, 27 };
907
908 // put to 2 for second layer
909 for (Int_t i=0; i<1; ++i)
910 {
911 if (!xSections[i])
912 continue;
913
914 TH1* xSection = xSections[i];
915 TH2* fMvsL = (i == 0) ? fMvsL1: fMvsL2;
916
a9aed06c 917 //Int_t nCuts = 6;
918 //Int_t cuts[] = { 0, 164, 178, 190, 204, 216 };
f91bc12d 919 //Int_t nCuts = 4;
920 //Int_t cuts[] = { 0, 164, 190, 216 };
d1594f8a 921
922 //Int_t nCuts = 4;
923 //Int_t cuts[] = { 0, 114, 145, 165 };
924 //Float_t ratePerTrigger[] = { 60, 13.3, 13.3, 13.3 };
925
926 Int_t nCuts = 3;
51f6de65 927 Int_t cuts[] = { 0, 114, 148 };
928
929 //Int_t nCuts = 3;
930 //Int_t cuts[] = { 0, 126, 162 };
931 //Float_t ratePerTrigger[] = { 60, 20.0, 20.0 };
a9aed06c 932
f91bc12d 933 // desired trigger rate in Hz
51f6de65 934 Float_t ratePerTrigger[] = { 100, 1, 1, 1, 1, 1 };
f91bc12d 935
936 xSection->SetStats(kFALSE);
937 xSection->SetTitle(""); //(i == 0) ? "SPD Layer 1" : "SPD Layer 2");
938 xSection->GetXaxis()->SetTitle(Form("true multiplicity in |#eta| < %.1f", (i == 0) ? 2.0 : 1.5));
939 xSection->GetXaxis()->SetRangeUser(0, (i == 0) ? 450 : 350);
940 //xSection->GetYaxis()->SetTitle("relative cross section");
941 xSection->GetYaxis()->SetTitleOffset(1.2);
942
943 // relative x-section, once we have a collision
944 xSection->Scale(1.0 / xSection->Integral());
945
946 TCanvas* canvas2 = new TCanvas(Form("HMPlots2_%d_Random", i), Form("HMPlots2_%d_Random", i), 800, 600);
947 canvas2->SetTopMargin(0.05);
948 canvas2->SetRightMargin(0.05);
949 canvas2->SetLogy();
d1594f8a 950
951 if (relative)
952 xSection->DrawCopy("HIST");
f91bc12d 953
954 TLegend* legend2 = new TLegend(0.15, 0.15, 0.6, 0.4);
955 legend2->SetFillColor(0);
956 legend2->AddEntry(xSection, "cross-section");
957
958 for (Int_t currentCut = 0; currentCut<nCuts; ++currentCut)
959 {
960 Int_t cut = cuts[currentCut];
961
d1594f8a 962 TH1* triggerEff = (TH1*) GetTriggerEfficiency(fMvsL, cut)->Clone("triggerEff");
963
f91bc12d 964 TH1* proj = GetXSectionCut(xSection, fMvsL, cut);
965
d1594f8a 966 Float_t triggerLimit = 0;
967 for (Int_t bin = 1; bin <= triggerEff->GetNbinsX(); bin++)
968 if (triggerEff->GetBinContent(bin) < 0.5)
969 triggerLimit = triggerEff->GetXaxis()->GetBinCenter(bin);
970
971 Printf("Efficiency limit (50%%) is at multiplicity %f", triggerLimit);
972
f91bc12d 973 Double_t total = 0;
974 if (proj->Integral(1, 1000) > 0)
975 total = proj->Integral(1, 1000);
976
977 printf("Cut at %d: rel. x-section = %e\n", cut, total);
978
979 TH1* proj2 = (TH1*) proj->Clone("random2");
980 proj2->Reset();
981
982 // calculate downscale factor
983 Float_t normalRate = rate * proj->Integral(1, 1000);
984 Float_t downScale = normalRate / ratePerTrigger[currentCut];
985 if (downScale < 1)
986 downScale = 1;
987 Long64_t nTrigger = (Long64_t) (normalRate / downScale * lengthRun);
dd367a14 988 nTrigger = TMath::Nint(((Float_t) nTrigger) / 1000) * 1000;
f91bc12d 989
990 Printf("Normal rate is %f, downscale: %f, Simulating %lld triggers", normalRate, downScale, nTrigger);
51f6de65 991 if (nTrigger == 0)
992 continue;
993
f91bc12d 994 proj2->FillRandom(proj, nTrigger);
995
996 Int_t removed = 0;
997 for (Int_t bin=1; bin<proj2->GetNbinsX(); ++bin)
998 if (proj2->GetBinContent(bin) < 5)
999 {
1000 removed += (Int_t) proj2->GetBinContent(bin);
1001 proj2->SetBinContent(bin, 0);
1002 }
1003
1004 Printf("Removed %d events", removed);
1005
d1594f8a 1006 if (relative)
1007 proj2->Scale(1.0 / nTrigger * proj->Integral(1, 1000));
f91bc12d 1008
1009 proj2->SetLineColor(colors[currentCut]);
1010 proj2->SetMarkerStyle(markers[currentCut]);
1011 proj2->SetMarkerColor(colors[currentCut]);
d1594f8a 1012
1013 if (relative || currentCut > 0) {
1014 proj2->DrawCopy("SAME P");
1015 } else
1016 proj2->DrawCopy(" P");
1017
745d6088 1018 TString eventStr;
1019 if (nTrigger > 1e6)
1020 {
1021 eventStr.Form("%lld M", nTrigger / 1000 / 1000);
1022 }
1023 else if (nTrigger > 1e3)
1024 {
1025 eventStr.Form("%lld K", nTrigger / 1000);
1026 }
1027 else
1028 eventStr.Form("%lld", nTrigger);
1029
1030 TString triggerStr;
1031 if (cut == 0)
1032 {
1033 triggerStr = "minimum bias";
1034 }
1035 else
1036 triggerStr.Form("FO > %d chips", cut);
d1594f8a 1037
745d6088 1038 legend2->AddEntry(proj2, Form("%s evts, %s", eventStr.Data(), triggerStr.Data()));
1039
1040 if (triggerLimit > 1)
1041 {
1042 TLine* line = new TLine(triggerLimit, proj2->GetMinimum(), triggerLimit, proj2->GetMaximum());
1043 line->SetLineColor(colors[currentCut]);
1044 line->Draw();
1045 }
f91bc12d 1046 }
1047
1048 legend2->Draw();
1049
1050 canvas2->SaveAs(Form("%s.gif", canvas2->GetName()));
1051 canvas2->SaveAs(Form("%s.eps", canvas2->GetName()));
1052 }
1053}
1054
d1594f8a 1055void AliHighMultiplicitySelector::Contamination()
1056{
1057 //
d1594f8a 1058 //
1059
1060 /*
1061
1062 gSystem->Load("libANALYSIS");
1063 gSystem->Load("libPWG0base");
1064 .L AliHighMultiplicitySelector.cxx+g
1065 x = new AliHighMultiplicitySelector();
1066 x->ReadHistograms("highmult_hijing100k.root");
1067 x->Contamination();
1068
1069 */
1070
1071 // get x-sections
1072 TFile* file = TFile::Open("crosssectionEx.root");
1073 if (!file)
1074 return;
1075
1076 TH1* xSections[2];
1077 xSections[0] = dynamic_cast<TH1*> (gFile->Get("xSection2Ex"));
1078 xSections[1] = dynamic_cast<TH1*> (gFile->Get("xSection15Ex"));
1079
1080 // rate = L * sigma
1081 // sigma ~ 80 mb (Pythia 14 TeV)
1082 // 10^28 lum --> 8e2 Hz
1083 // 10^31 lum --> 8e5 Hz
1084 Double_t rates[] = { 8e2, 8e3, 8e4, 8e5 };
1085
1086 Int_t nCuts = 4;
1087 Int_t cuts[] = { 104, 134, 154, 170 };
1088
1089 // put to 2 for second layer
1090 for (Int_t i=0; i<1; ++i)
1091 {
1092 if (!xSections[i])
1093 continue;
1094
1095 // relative x-section, once we have a collision
1096 xSections[i]->Scale(1.0 / xSections[i]->Integral());
1097
1098 Int_t max = xSections[i]->GetNbinsX();
1099 max = 500;
1100
1101 Float_t* xSection = new Float_t[max];
1102 for (Int_t mult = 0; mult < max; mult++)
1103 xSection[mult] = xSections[i]->GetBinContent(mult+1);
1104
1105 TH2* fMvsL = (i == 0) ? fMvsL1: fMvsL2;
1106
1107 TGraph* graph = new TGraph;
1108
1109 for (Int_t currentCut = 0; currentCut<nCuts; ++currentCut)
1110 {
1111 Int_t cut = cuts[currentCut];
1112 Double_t rate = rates[currentCut];
1113 //Double_t rate = rates[3];
1114
1115 // coll. in 100 ns window
69b09e3b 1116 Double_t windowSize = 100e-9;
1117 //Double_t windowSize = 25e-9;
d1594f8a 1118 Double_t collPerWindow = windowSize * rate;
1119 Printf("coll/window = %f", collPerWindow);
1120 Double_t windowsPerSecond = 1.0 / windowSize;
1121
1122 TH1* triggerEffHist = (TH1*) GetTriggerEfficiency(fMvsL, cut)->Clone("triggerEff");
335a5e1b 1123 Float_t* triggerEff = new Float_t[max*2];
d1594f8a 1124 for (Int_t mult = 0; mult < max; mult++)
1125 triggerEff[mult] = triggerEffHist->GetBinContent(mult+1);
1126
1127 Double_t triggerRate = 0;
1128 for (Int_t mult = 0; mult < max; mult++)
1129 triggerRate += xSection[mult] * triggerEff[mult];
1130
1131 triggerRate *= TMath::Poisson(1, collPerWindow) * windowsPerSecond;
1132
1133 Printf("Rate for 1 collision is %f Hz", triggerRate);
1134
1135 Double_t triggerRate2 = 0;
1136 for (Int_t mult = 0; mult < max; mult++)
1137 for (Int_t mult2 = mult; mult2 < max; mult2++)
1138 if (mult+mult2 < max)
1139 triggerRate2 += ((mult2 > mult) ? 2. : 1.) * xSection[mult] * xSection[mult2] * triggerEff[mult+mult2];
1140
1141 triggerRate2 *= TMath::Poisson(2, collPerWindow) * windowsPerSecond;
d1594f8a 1142
1143 Printf("Rate for 2 collisions is %f Hz --> %.1f%%", triggerRate2, triggerRate2 / triggerRate * 100);
1144
1145 Double_t triggerRate3 = 0;
144ff489 1146
d1594f8a 1147 for (Int_t mult = 0; mult < max; mult++)
1148 for (Int_t mult2 = mult; mult2 < max-mult; mult2++)
1149 for (Int_t mult3 = 0; mult3 < max-mult-mult2; mult3++)
1150 //if (mult+mult2+mult3 < max)
1151 triggerRate3 += ((mult2 > mult) ? 2. : 1.) * xSection[mult] * xSection[mult2] * xSection[mult3] * triggerEff[mult+mult2+mult3];
1152
1153 triggerRate3 *= TMath::Poisson(3, collPerWindow) * windowsPerSecond;
1154 //triggerRate3 *= collPerWindow * collPerWindow * rate;
1155
1156 Printf("Rate for 3 collisions is %f Hz --> %.1f%%", triggerRate3, triggerRate3 / triggerRate * 100);
1157
1158 Float_t totalContamination = (triggerRate2 + triggerRate3) / (triggerRate + triggerRate2 + triggerRate3);
1159
1160 Printf("Total contamination is %.1f%%", totalContamination * 100);
1161
1162 graph->SetPoint(graph->GetN(), cut, totalContamination);
1163
1164 continue;
1165
1166 Double_t triggerRate4 = 0;
1167 for (Int_t mult = 0; mult < max; mult++)
1168 for (Int_t mult2 = mult; mult2 < max-mult; mult2++)
1169 for (Int_t mult3 = 0; mult3 < max-mult-mult2; mult3++)
1170 for (Int_t mult4 = 0; mult4 < max-mult-mult2-mult3; mult4++)
1171 //if (mult+mult2+mult3+mult4 < max)
1172 triggerRate4 += ((mult2 > mult) ? 2. : 1.) * xSection[mult] * xSection[mult2] * xSection[mult3] * xSection[mult4] * triggerEff[mult+mult2+mult3+mult4];
1173
1174 //triggerRate4 *= collPerWindow * collPerWindow * collPerWindow * rate;
1175 triggerRate4 *= TMath::Poisson(4, collPerWindow) * windowsPerSecond;
1176
1177 Printf("Rate for 4 collisions is %f Hz --> %.1f%%", triggerRate4, triggerRate4 / triggerRate * 100);
1178
1179 // general code for n collisions follows, however much slower...
1180 /*
1181 const Int_t maxdepth = 4;
1182 for (Int_t depth = 1; depth <= maxdepth; depth++) {
1183 Double_t triggerRate = 0;
1184
1185 Int_t m[maxdepth];
1186 for (Int_t d=0; d<maxdepth; d++)
1187 m[d] = 0;
1188
1189 while (m[0] < max) {
1190 Double_t value = 1;
1191 Int_t sum = 0;
1192 for (Int_t d=0; d<depth; d++) {
1193 value *= xSection[m[d]];
1194 sum += m[d];
1195 }
1196
1197 if (sum < max) {
1198 value *= triggerEff[sum];
1199 triggerRate += value;
1200 }
1201
1202 Int_t increase = depth-1;
1203 ++m[increase];
1204 while (m[increase] == max && increase > 0) {
1205 m[increase] = 0;
1206 --increase;
1207 ++m[increase];
1208 }
1209 }
1210
1211 triggerRate *= rate * TMath::Power(collPerWindow, depth - 1);
1212
1213 Printf("Rate for %d collisions is %f Hz", depth, triggerRate);
1214 }*/
1215 }
1216
1217 new TCanvas; graph->Draw("AP*");
1218 }
1219}
1220
144ff489 1221void AliHighMultiplicitySelector::Contamination2()
1222{
1223 //
1224 // produces a spectrum created with N triggers
1225 // number of triggers and thresholds for the moment fixed
1226 //
1227
1228 /*
1229
1230 gSystem->Load("libANALYSIS");
1231 gSystem->Load("libPWG0base");
1232 .L AliHighMultiplicitySelector.cxx+g
1233 x = new AliHighMultiplicitySelector();
1234 x->ReadHistograms("highmult_hijing100k.root");
1235 x->Contamination2();
1236
1237 */
1238
1239 // get x-sections
1240 TFile* file = TFile::Open("crosssectionEx.root");
1241 if (!file)
1242 return;
1243
1244 TH1* xSections[2];
1245 xSections[0] = dynamic_cast<TH1*> (gFile->Get("xSection2Ex"));
1246 xSections[1] = dynamic_cast<TH1*> (gFile->Get("xSection15Ex"));
1247
1248 Int_t nCuts = 4;
1249 Int_t cuts[] = { 104, 134, 154, 170 };
1250
1251 new TCanvas;
1252
1253 Int_t colors[] = { 2, 3, 4, 6, 7, 8 };
1254 Int_t markers[] = { 7, 2, 4, 5, 6, 27 };
1255
1256 // put to 2 for second layer
1257 for (Int_t i=0; i<1; ++i)
1258 {
1259 if (!xSections[i])
1260 continue;
1261
1262 // relative x-section, once we have a collision
1263 xSections[i]->Scale(1.0 / xSections[i]->Integral());
1264
1265 Int_t max = xSections[i]->GetNbinsX();
1266 max = 500;
1267
1268 Float_t* xSection = new Float_t[max];
1269 for (Int_t mult = 0; mult < max; mult++)
1270 xSection[mult] = xSections[i]->GetBinContent(mult+1);
1271
1272 TH2* fMvsL = (i == 0) ? fMvsL1: fMvsL2;
1273
1274 for (Int_t currentCut = 0; currentCut<nCuts; ++currentCut)
1275 {
1276 TGraph* graph = new TGraph;
1277 graph->SetMarkerColor(colors[currentCut]);
1278 graph->SetMarkerStyle(markers[currentCut]);
1279
1280 Int_t cut = cuts[currentCut];
1281
1282 TH1* triggerEffHist = (TH1*) GetTriggerEfficiency(fMvsL, cut)->Clone("triggerEff");
335a5e1b 1283 Float_t* triggerEff = new Float_t[max*2];
144ff489 1284 for (Int_t mult = 0; mult < max; mult++)
1285 triggerEff[mult] = triggerEffHist->GetBinContent(mult+1);
1286
1287 Double_t triggerRate = 0;
1288 for (Int_t mult = 0; mult < max; mult++)
1289 triggerRate += xSection[mult] * triggerEff[mult];
1290
1291 Printf("Raw value for 1 collision is %e", triggerRate);
1292
1293 Double_t triggerRate2 = 0;
1294 for (Int_t mult = 0; mult < max; mult++)
1295 for (Int_t mult2 = mult; mult2 < max; mult2++)
1296 if (mult+mult2 < max)
1297 triggerRate2 += ((mult2 > mult) ? 2. : 1.) * xSection[mult] * xSection[mult2] * triggerEff[mult+mult2];
1298
1299 Printf("Raw value for 2 collisions is %e", triggerRate2);
1300
69b09e3b 1301 for (Double_t doubleRate = 0; doubleRate <= 0.3; doubleRate += 0.005)
144ff489 1302 {
1303 Float_t totalContamination = (triggerRate2 * doubleRate) / (triggerRate + triggerRate2 * doubleRate);
1304
1305 //Printf("Total contamination is %.1f%%", totalContamination * 100);
1306
1307 graph->SetPoint(graph->GetN(), doubleRate, totalContamination);
1308 }
1309
1310 graph->Draw((currentCut == 0) ? "A*" : "* SAME");
1311 graph->GetXaxis()->SetRangeUser(0, 1);
1312 }
1313 }
1314}
1315
69b09e3b 1316void AliHighMultiplicitySelector::Contamination3()
1317{
1318 //
b3b260d1 1319 // draws the contamination as function of treshold depending on a number a set of input MC and rate parameters
69b09e3b 1320 //
1321
1322 /*
1323
1324 gSystem->Load("libANALYSIS");
1325 gSystem->Load("libPWG0base");
1326 .L AliHighMultiplicitySelector.cxx+g
1327 x = new AliHighMultiplicitySelector();
1328 x->ReadHistograms("highmult_hijing100k.root");
1329 x->Contamination3();
1330
1331 */
1332
b3b260d1 1333 // output file
1334 TFile* output = TFile::Open("contamination3.root", "RECREATE");
1335
69b09e3b 1336 // get x-sections
b3b260d1 1337 TFile* file = TFile::Open("crosssectionEx_10TeV.root");
69b09e3b 1338 if (!file)
1339 return;
b3b260d1 1340
1341 TCanvas* c = new TCanvas;
1342 c->SetGridx();
1343 c->SetGridy();
1344
1345 TLegend* legend = new TLegend(0.7, 0.2, 1, 0.5);
1346 legend->SetNColumns(2);
1347
1348 TH2* dummy = new TH2F("dummy", ";Layer 1 Threshold;Contamination", 100, 95, 255, 100, 0, 1);
1349 dummy->SetStats(kFALSE);
1350 dummy->Draw();
1351
1352 for (Int_t mc = 0; mc < 6; mc++)
69b09e3b 1353 {
b3b260d1 1354 TH1* xSections[2];
1355 TString str;
1356 str.Form("xSection2Ex_%d_%d", mc/3, mc%3);
1357 Printf("%s", str.Data());
1358 file->cd();
1359 xSections[0] = dynamic_cast<TH1*> (gFile->Get(str));
1360 //xSections[1] = dynamic_cast<TH1*> (gFile->Get("xSection15Ex"));
1361
1362 // prob for a collision in a bunch crossing
1363 Int_t nRates = 1;
1364 //Float_t rates[] = {0.02, 0.05, 0.1, 0.15, 0.2};
1365 Float_t rates[] = {0.0636};
1366
1367 // bunch crossing rate in Hz
1368 Float_t bunchCrossingRate = 24. * 11245.5;
1369
1370 Int_t colors[] = { 2, 3, 4, 6, 7, 8 };
1371 Int_t markers[] = { 7, 2, 4, 5, 6, 27 };
1372
1373 // put to 2 for second layer
1374 for (Int_t i=0; i<1; ++i)
69b09e3b 1375 {
b3b260d1 1376 if (!xSections[i])
1377 continue;
1378
1379 // relative x-section, once we have a collision
1380 xSections[i]->Scale(1.0 / xSections[i]->Integral());
1381
1382 Int_t max = xSections[i]->GetNbinsX();
1383 max = 500;
1384
1385 Float_t* xSection = new Float_t[max];
1386 for (Int_t mult = 0; mult < max; mult++)
1387 xSection[mult] = xSections[i]->GetBinContent(mult+1);
1388
1389 TH2* fMvsL = (i == 0) ? fMvsL1: fMvsL2;
1390
1391 for (Int_t currentRate = 0; currentRate<nRates; ++currentRate)
69b09e3b 1392 {
b3b260d1 1393 TGraph* graph = new TGraph;
1394 graph->SetMarkerColor(colors[currentRate]);
1395 graph->SetMarkerStyle(markers[currentRate]);
1396
1397 TGraph* graph2 = new TGraph;
1398
1399 Float_t rate = rates[currentRate];
1400
1401 Double_t singleRate = TMath::Poisson(1, rate);
1402 Double_t doubleRate = TMath::Poisson(2, rate);
1403 Double_t tripleRate = TMath::Poisson(3, rate);
1404
1405 Printf("single = %f, double = %f, triple = %f", singleRate, doubleRate, tripleRate);
1406
1407 for (Int_t cut = 100; cut <= 251; cut += 10)
1408 {
1409 Printf("Cut at %d", cut);
1410
1411 TH1* triggerEffHist = (TH1*) GetTriggerEfficiency(fMvsL, cut)->Clone("triggerEff");
335a5e1b 1412 Float_t* triggerEff = new Float_t[max*2];
b3b260d1 1413 for (Int_t mult = 0; mult < max; mult++)
1414 triggerEff[mult] = triggerEffHist->GetBinContent(mult+1);
1415
1416 Double_t triggerRate = 0;
1417 for (Int_t mult = 0; mult < max; mult++)
1418 triggerRate += xSection[mult] * triggerEff[mult];
1419
1420 //Printf(" Raw value for 1 collision is %e; Rate: %.1f Hz", triggerRate, triggerRate * singleRate * bunchCrossingRate);
1421
1422 Double_t triggerRate2 = 0;
1423 for (Int_t mult = 0; mult < max; mult++)
1424 for (Int_t mult2 = mult; mult2 < max; mult2++)
1425 if (mult+mult2 < max)
1426 triggerRate2 += ((mult2 > mult) ? 2. : 1.) * xSection[mult] * xSection[mult2] * triggerEff[mult+mult2];
1427
1428 //Printf(" Raw value for 2 collisions is %e; Rate: %.1f Hz", triggerRate2, triggerRate2 * doubleRate * bunchCrossingRate);
1429
1430 Double_t triggerRate3 = 0;
1431 for (Int_t mult = 0; mult < max; mult++)
1432 for (Int_t mult2 = 0; mult2 < max; mult2++)
1433 for (Int_t mult3 = 0; mult3 < max; mult3++)
1434 if (mult+mult2+mult3 < max)
1435 triggerRate3 += xSection[mult] * xSection[mult2] * xSection[mult3] * triggerEff[mult+mult2+mult3];
1436
1437 //Printf(" Raw value for 3 collisions is %e; Rate: %.1f Hz", triggerRate3, triggerRate3 * tripleRate * bunchCrossingRate);
1438
1439 Printf(" Rates: %.1f Hz; %.1f Hz; %.1f Hz", triggerRate * singleRate * bunchCrossingRate, triggerRate2 * doubleRate * bunchCrossingRate, triggerRate3 * tripleRate * bunchCrossingRate);
1440
1441 Float_t totalTrigger = (triggerRate * singleRate + triggerRate2 * doubleRate + triggerRate3 * tripleRate);
1442
1443 Printf(" Total trigger rate: %.1f Hz", totalTrigger * bunchCrossingRate);
1444
1445 //if (totalTrigger * bunchCrossingRate > 200)
1446 // continue;
1447
1448 Float_t totalContamination = (triggerRate2 * doubleRate + triggerRate3 * tripleRate) / totalTrigger;
1449 //if (totalContamination > 0.99)
1450 // break;
1451
1452 Printf(" Total contamination is %.1f%%", totalContamination * 100);
1453
1454 graph->SetPoint(graph->GetN(), cut, totalContamination);
1455 graph2->SetPoint(graph->GetN(), cut, totalTrigger * bunchCrossingRate);
1456 }
1457
1458 graph->SetMarkerStyle(mc+20);
1459 graph->SetMarkerColor(currentRate+1);
1460 graph->Draw("P SAME");
1461 graph->GetXaxis()->SetTitle("Layer 1 threshold");
1462 graph->GetYaxis()->SetTitle("Contamination");
1463 graph->GetYaxis()->SetRangeUser(0, 1);
1464
1465 if (currentRate == 0)
1466 {
1467 const char* legendLabel[] = { "Pythia Slope 1", "Pythia Slope 2", "Pythia Slope 3", "Phojet Slope 1", "Phojet Slope 2", "Phojet Slope 3" };
1468 legend->AddEntry(graph, legendLabel[mc], "P");
1469 }
69b09e3b 1470
b3b260d1 1471 output->cd();
1472 graph->Write(Form("%s_%d_cont", str.Data(), currentRate));
1473 graph2->Write(Form("%s_%d_rate", str.Data(), currentRate));
1474 }
1475 }
1476 }
1477
1478 output->Close();
1479
1480 legend->Draw();
1481}
69b09e3b 1482
b3b260d1 1483void AliHighMultiplicitySelector::Contamination_Reach()
1484{
1485 // plot the multiplicity reach based on the output from Contamination3()
1486 // for each rate case and each MC, a certain number of events is required starting counting from the highest multiplicity
1487 // note that the reach of different MC cannot be compared with each other
69b09e3b 1488
b3b260d1 1489 /*
69b09e3b 1490
b3b260d1 1491 gSystem->Load("libANALYSIS");
1492 gSystem->Load("libPWG0base");
1493 .L AliHighMultiplicitySelector.cxx+g
1494 x = new AliHighMultiplicitySelector();
1495 x->ReadHistograms("highmult_hijing100k.root");
1496 x->Contamination_Reach();
69b09e3b 1497
b3b260d1 1498 */
69b09e3b 1499
b3b260d1 1500 TCanvas* c = new TCanvas("c", "c", 800, 600);
1501 c->Divide(2, 3);
1502
1503 // prob for a collision in a bunch crossing
1504 Int_t nRates = 1;
1505 //Float_t rates[] = {0.02, 0.05, 0.1, 0.15, 0.2};
1506 Float_t rates[] = {0.0636};
69b09e3b 1507
b3b260d1 1508 // bunch crossing rate in Hz
1509 Float_t bunchCrossingRate = 24. * 11245.5;
69b09e3b 1510
b3b260d1 1511 TH2* dummy = new TH2F("dummy", ";Coll/bunch crossing;multiplicity reach", 100, 0, 0.3, 100, 50, 350);
1512 //TH2* dummy = new TH2F("dummy", ";Coll/bunch crossing;fractional cross-section", 100, 0, 0.3, 1000, 1e-6, 0.1);
1513 dummy->SetStats(kFALSE);
69b09e3b 1514
b3b260d1 1515 const char* legendLabel[] = { "Pythia Slope 1", "Pythia Slope 2", "Pythia Slope 3", "Phojet Slope 1", "Phojet Slope 2", "Phojet Slope 3" };
69b09e3b 1516
b3b260d1 1517 TFile* mcFile = TFile::Open("crosssectionEx_10TeV.root");
1518 TFile* contFile = TFile::Open("contamination3.root");
69b09e3b 1519
b3b260d1 1520 // for comparison: how many MB events can one take at the same time
ad0385e9 1521 Int_t mbEvents = 2000000 * 500;
69b09e3b 1522
b3b260d1 1523 for (Int_t mc=0; mc<6; mc++)
1524 {
1525 mcFile->cd();
1526 TH1* mcHist = (TH1*) gFile->Get(Form("xSection2Ex_%d_%d", mc/3, mc%3));
1527 mcHist->Scale(1.0 / mcHist->Integral());
1528
1529 c->cd(mc+1);//->SetLogy();
1530 c->SetGridx();
1531 c->SetGridy();
1532 dummy->Draw();
1533
1534 Int_t color = 0;
1535 for (Int_t requiredEvents = 300; requiredEvents <= 3000000; requiredEvents *= 10)
1536 {
1537 TGraph* reach = new TGraph;
1538
1539 color++;
1540 if (color == 5)
1541 color++;
1542
1543 Float_t requiredRate = (Float_t) requiredEvents / 1e6;
1544 Printf("Required rate is %f", requiredRate);
1545
1546 // find reach without trigger
1547 Int_t mbReach = 1000;
1548 while (mcHist->Integral(mcHist->FindBin(mbReach), mcHist->GetNbinsX()) < (Float_t) requiredEvents / mbEvents && mbReach > 1)
1549 mbReach--;
1550 Printf("MB reach is %d with %f events", mbReach, mcHist->Integral(mcHist->FindBin(mbReach), mcHist->GetNbinsX()) * mbEvents);
1551
1552 for (Int_t rate=0; rate<nRates; rate++)
1553 {
1554 contFile->cd();
1555 TGraph* cont = (TGraph*) gFile->Get(Form("xSection2Ex_%d_%d_%d_cont", mc/3, mc%3, rate));
1556 TGraph* rateh = (TGraph*) gFile->Get(Form("xSection2Ex_%d_%d_%d_rate", mc/3, mc%3, rate));
1557
1558 Double_t singleRate = TMath::Poisson(1, rates[rate]);
1559 Double_t totalCollRate = singleRate * bunchCrossingRate;
1560 Printf("collisions/bc: %f; coll. rate: %f", singleRate, totalCollRate);
1561
1562 // find 200 Hz limit
1563 Int_t low = 100;
1564 while (rateh->Eval(low) > 200)
1565 low++;
1566
1567 // find contamination limit
1568 Int_t high = 100;
1569 while (cont->Eval(high) < 0.9 && high < 250)
1570 high++;
1571
1572 Printf("MC %d Rate %d: Acceptable threshold region is %d to %d", mc, rate, low, high);
1573 // find reachable multiplicity; include contamination in rate calculation
1574 // TH1* triggerEffHist = (TH1*) GetTriggerEfficiency(fMvsL, cut)->Clone("triggerEff");
1575
1576 // trigger efficiency as function of multiplicity in range mult <= ... <= high
1577 //new TCanvas; fMvsL1->Draw("COLZ");
1578 TH1* triggerEffHist = (TH1*) GetTriggerEfficiency(fMvsL1, low, high);
1579
1580 //new TCanvas; triggerEffHist->DrawCopy();
1581 triggerEffHist->Multiply(mcHist);
1582
1583 Float_t fractionXSection = triggerEffHist->Integral();
1584 Printf("The fraction of the cross-section is %f", fractionXSection);
1585
1586 //new TCanvas; triggerEffHist->DrawCopy();
1587 triggerEffHist->Scale(totalCollRate);
1588 //new TCanvas; triggerEffHist->DrawCopy(); gPad->SetLogy();
1589
1590 Float_t achievedRate = 0;
1591 Int_t mult = 1000;
1592 while (1)
1593 {
1594 achievedRate = triggerEffHist->Integral(triggerEffHist->FindBin(mult), triggerEffHist->GetNbinsX());
1595
1596 if (achievedRate >= requiredRate)
1597 break;
1598
1599 if (mult == 1)
1600 break;
1601
1602 mult--;
1603 }
1604
1605 Printf("Achieved rate %f above multiplicity %d", achievedRate, mult);
1606
1607 if (achievedRate < requiredRate)
1608 {
1609 Printf("Achieved rate too low");
1610 continue;
1611 }
1612
1613 reach->SetPoint(reach->GetN(), rates[rate], mult);
1614 //reach->SetPoint(reach->GetN(), rates[rate], fractionXSection);
1615
1616
1617 //return;
69b09e3b 1618 }
b3b260d1 1619
1620 reach->SetMarkerColor(color);
1621 reach->Draw("SAME*");
1622
1623 TLine* line = new TLine(0, mbReach, 0.3, mbReach);
1624 line->SetLineColor(color);
1625 //line->Draw();
1626 }
1627
1628 TText* text = new TText;
1629 text->DrawText(0.2, 325, legendLabel[mc]);
1630 //return;
69b09e3b 1631 }
1632}
1633
9608df41 1634void AliHighMultiplicitySelector::DrawHistograms()
1635{
a9aed06c 1636 // draws the histograms
1637
9608df41 1638 /*
1639
1640 gSystem->Load("libPWG0base");
1641 .L AliHighMultiplicitySelector.cxx+
1642 x = new AliHighMultiplicitySelector();
1643 x->ReadHistograms("highmult_pythia.root");
1644 x->DrawHistograms();
1645
1646
1647 gSystem->Load("libPWG0base");
1648 .L AliHighMultiplicitySelector.cxx+
1649 x = new AliHighMultiplicitySelector();
1650 x->ReadHistograms("highmult_hijing.root");
1651 x->DrawHistograms();
1652
1653 gSystem->Load("libPWG0base");
1654 .L AliHighMultiplicitySelector.cxx+
1655 x = new AliHighMultiplicitySelector();
1656 x->ReadHistograms("highmult_central.root");
1657 x->DrawHistograms();
1658
745d6088 1659 gSystem->Load("libANALYSIS");
9608df41 1660 gSystem->Load("libPWG0base");
70fdd197 1661 .L AliHighMultiplicitySelector.cxx++
9608df41 1662 x = new AliHighMultiplicitySelector();
1663 x->ReadHistograms("highmult_hijing100k.root");
1664 x->DrawHistograms();
1665
1666 */
1667
1668 /*TCanvas* canvas = new TCanvas("chips", "chips", 600, 400);
1669
1670 fChipsLayer2->SetLineColor(2);
1671 fChipsLayer2->SetStats(kFALSE);
1672 fChipsLayer1->SetStats(kFALSE);
1673 fChipsLayer2->SetTitle("");
1674 fChipsLayer2->DrawCopy();
1675 fChipsLayer1->DrawCopy("SAME");
1676 canvas->SaveAs("chips.gif");
1677
1678 canvas = new TCanvas("L1vsL2", "L1vsL2", 600, 400);
1679 fL1vsL2->SetStats(kFALSE);
1680 fL1vsL2->DrawCopy("COLZ");
1681 gPad->SetLogz();
1682 canvas->SaveAs("L1vsL2.gif");*/
1683
f6093269 1684 TCanvas *canvas = new TCanvas("L1", "L1", 800, 600);
1685 canvas->SetTopMargin(0.05);
1686 canvas->SetRightMargin(0.12);
9608df41 1687 fMvsL1->SetStats(kFALSE);
1688 fMvsL1->DrawCopy("COLZ");
1689 gPad->SetLogz();
1690
1691 canvas->SaveAs("L1NoCurve.gif");
f6093269 1692 canvas->SaveAs("L1NoCurve.eps");
9608df41 1693
745d6088 1694 TLine* line = new TLine(fMvsL1->GetXaxis()->GetXmin(), 150, fMvsL1->GetXaxis()->GetXmax(), 150);
1695 line->SetLineWidth(2);
1696 line->SetLineColor(kRed);
1697 line->Draw();
1698
1699 canvas->SaveAs("L1NoCurveCut.gif");
1700 canvas->SaveAs("L1NoCurveCut.eps");
1701
1702 return;
1703
9608df41 1704 // draw corresponding theoretical curve
1705 TF1* func = new TF1("func", "[0]*(1-(1-1/[0])**x)", 1, 1000);
1706 func->SetParameter(0, 400-5*2);
1707 func->DrawCopy("SAME");
1708
1709 canvas->SaveAs("L1.gif");
1710
1711 canvas = new TCanvas("L2", "L2", 600, 400);
1712 //fMvsL2->GetYaxis()->SetRangeUser(0, 150);
1713 fMvsL2->SetStats(kFALSE);
1714 fMvsL2->DrawCopy("COLZ");
1715 gPad->SetLogz();
1716 func->SetParameter(0, 800-5*4);
1717 func->DrawCopy("SAME");
1718 canvas->SaveAs("L2.gif");
1719
f6093269 1720 // get x-sections
1721 TFile* file = TFile::Open("crosssectionEx.root");
1722 if (file)
1723 {
1724 TH1* xSection2 = dynamic_cast<TH1*> (gFile->Get("xSection2Ex"));
1725 TH1* xSection15 = dynamic_cast<TH1*> (gFile->Get("xSection15Ex"));
1726
1727 MakeGraphs2("Layer1", xSection2, fMvsL1);
1728 return;
1729
1730 // 5 times the mean
1731 //MakeGraphs("Layer1", xSection2, fMvsL1, (Int_t) (xSection2->GetMean() * 5)); //75 * 2 * 2);
1732 //MakeGraphs("Layer2", xSection15, fMvsL2, (Int_t) (xSection15->GetMean() * 5)); //(Int_t) (75 * 1.5 * 2));
1733
1734 MakeGraphs("Layer1", xSection2, fMvsL1, (Int_t) (xSection2->GetMean() * 8));
1735 MakeGraphs("Layer2", xSection15, fMvsL2, (Int_t) (xSection15->GetMean() * 8));
1736 MakeGraphs("Layer1", xSection2, fMvsL1, (Int_t) (xSection2->GetMean() * 9));
1737 MakeGraphs("Layer2", xSection15, fMvsL2, (Int_t) (xSection15->GetMean() * 9));
1738 MakeGraphs("Layer1", xSection2, fMvsL1, (Int_t) (xSection2->GetMean() * 10));
1739 MakeGraphs("Layer2", xSection15, fMvsL2, (Int_t) (xSection15->GetMean() * 10));
1740
1741 file->Close();
1742 }
1743
9608df41 1744 // make spread hists
1745 TGraph* spread = new TGraph;
1746 spread->SetTitle("Spread L1;true multiplicity;RMS");
1747
1748 for (Int_t i=1; i<=fMvsL1->GetNbinsX(); ++i)
1749 {
1750 TH1* proj = fMvsL1->ProjectionY("proj", i, i);
1751 spread->SetPoint(spread->GetN(), i, proj->GetRMS());
1752 }
1753
1754 canvas = new TCanvas("SpreadL1", "SpreadL1", 600, 400);
1755 spread->Draw("A*");
1756 canvas->SaveAs(Form("%s.gif", canvas->GetName()));
1757
1758 TF1* log = new TF1("log", "[0]*log([1]*x)", 1, 150);
1759 log->SetParLimits(0, 0, 10);
1760 log->SetParLimits(1, 1e-5, 10);
1761
1762 spread->Fit(log, "", "", 1, 150);
1763 log->DrawCopy("SAME");
1764
1765 TGraph* spread2 = new TGraph;
1766 spread2->SetTitle("Spread L2;true multiplicity;RMS");
1767
1768 for (Int_t i=1; i<=fMvsL1->GetNbinsX(); ++i)
1769 {
1770 TH1* proj = fMvsL2->ProjectionY("proj", i, i);
1771 spread2->SetPoint(spread2->GetN(), i, proj->GetRMS());
1772 }
1773
1774 canvas = new TCanvas("SpreadL2", "SpreadL2", 600, 400);
1775 spread2->Draw("A*");
1776 canvas->SaveAs(Form("%s.gif", canvas->GetName()));
1777
1778 spread2->Fit(log, "", "", 1, 150);
1779 log->DrawCopy("SAME");
1780
9608df41 1781 canvas = new TCanvas("Clusters_L1", "Clusters_L1", 600, 400);
1782 fClvsL1->SetStats(kFALSE);
1783 fClvsL1->DrawCopy("COLZ");
1784 gPad->SetLogz();
1785
1786 func->SetParameter(0, 400-5*2);
1787 func->DrawCopy("SAME");
1788
1789 canvas->SaveAs("Clusters_L1.gif");
1790
1791 canvas = new TCanvas("Clusters_L2", "Clusters_L2", 600, 400);
1792 fClvsL2->SetStats(kFALSE);
1793 fClvsL2->DrawCopy("COLZ");
1794 gPad->SetLogz();
1795 func->SetParameter(0, 800-5*4);
1796 func->DrawCopy("SAME");
1797 canvas->SaveAs("Clusters_L2.gif");
1798
1799 canvas = new TCanvas("ChipsFired", "ChipsFired", 600, 400);
1800 //fChipsFired->GetYaxis()->SetRangeUser(0, 150);
1801 fChipsFired->SetStats(kFALSE);
1802 fChipsFired->DrawCopy("COLZ");
1803 canvas->SaveAs("ChipsFired.gif");
1804
1805 /*TH1F* tresholdHistL1 = new TH1F("tresholdHistL1", ";chip treshold;<n>", BINNING_LAYER1);
1806 TH1F* tresholdHistL2 = new TH1F("tresholdHistL2", ";chip treshold;<n>", BINNING_LAYER2);
1807
1808 for (Int_t treshold = 0; treshold < 800; treshold++)
1809 {
1810 if (fPrimaryL1->Draw("multiplicity>>mult", Form("firedChips>%d", treshold), "goff") > 0)
1811 {
1812 TH1F* mult = dynamic_cast<TH1F*> (fPrimaryL1->GetHistogram());
1813 if (mult)
1814 tresholdHistL1->Fill(treshold, mult->GetMean());
1815 }
1816 if (fPrimaryL2->Draw("multiplicity>>mult", Form("firedChips>%d", treshold), "goff") > 0)
1817 {
1818 TH1F* mult = dynamic_cast<TH1F*> (fPrimaryL2->GetHistogram());
1819 if (mult)
1820 tresholdHistL2->Fill(treshold, mult->GetMean());
1821 }
1822 }
1823
1824 canvas = new TCanvas("TresholdL1", "TresholdL1", 600, 400);
1825 tresholdHistL1->Draw();
1826 canvas->SaveAs(Form("%s.gif", canvas->GetName()));
1827
1828 canvas = new TCanvas("TresholdL2", "TresholdL2", 600, 400);
1829 tresholdHistL2->Draw();
1830 canvas->SaveAs(Form("%s.gif", canvas->GetName()));*/
1831
1832 fPrimaryL1->Draw("(chipsByPrimaries/firedChips):multiplicity>>eff1", "", "prof goff");
1833 fPrimaryL2->Draw("(chipsByPrimaries/firedChips):multiplicity>>eff2", "", "prof goff");
1834
1835 canvas = new TCanvas("Efficiency", "Efficiency", 600, 400);
1836 fPrimaryL1->GetHistogram()->SetStats(kFALSE);
1837 fPrimaryL1->GetHistogram()->Draw();
1838 fPrimaryL2->GetHistogram()->SetLineColor(2);
1839 fPrimaryL2->GetHistogram()->SetStats(kFALSE);
1840 fPrimaryL2->GetHistogram()->Draw("SAME");
1841 canvas->SaveAs(Form("%s.gif", canvas->GetName()));
1842
1843 canvas = new TCanvas("ClustersZL1", "ClustersZL1", 600, 400);
1844 fClusterZL1->Rebin(2);
1845 fClusterZL1->Draw();
1846 canvas->SaveAs(Form("%s.gif", canvas->GetName()));
1847
1848 canvas = new TCanvas("ClustersZL2", "ClustersZL2", 600, 400);
1849 fClusterZL2->Draw();
1850 fClusterZL2->Rebin(2);
1851 canvas->SaveAs(Form("%s.gif", canvas->GetName()));
1852}
a9aed06c 1853
1854TGraph* AliHighMultiplicitySelector::IntFractRate()
1855{
1856 // A plot which shows the fractional rate above any threshold
1857 // as function of threshold (i.e. the integral of dSigma/dN as function of
1858 // N, normalised to 1 for N=0)
1859
1860 /*
d1594f8a 1861 gSystem->Load("libANALYSIS");
a9aed06c 1862 gSystem->Load("libPWG0base");
1863 .L AliHighMultiplicitySelector.cxx+
1864 x = new AliHighMultiplicitySelector();
1865 x->ReadHistograms("highmult_hijing100k.root");
1866 x->IntFractRate();
1867 */
1868
1869 // get x-sections
1870 TFile* file = TFile::Open("crosssectionEx.root");
1871 if (!file)
1872 return 0;
1873
1874 TH1* xSection;
335a5e1b 1875 xSection = static_cast<TH1*> (gFile->Get("xSection2Ex"));
a9aed06c 1876
1877 TGraph* result = new TGraph;
1878
1879 for (Int_t threshold = 0; threshold < 300; threshold += 2)
1880 {
1881 TH1* proj = GetXSectionCut(xSection, fMvsL1, threshold);
1882
1883 //new TCanvas; proj->DrawCopy();
1884
1885 Double_t integral = proj->Integral();
1886
d1594f8a 1887 Printf("Cut at %d, integral is %e", threshold, integral);
a9aed06c 1888
1889 result->SetPoint(result->GetN(), threshold, integral);
1890 }
1891
1892 TCanvas* canvas = new TCanvas("IntFractRate", "IntFractRate", 600, 400);
1893 gPad->SetLogy();
1894
1895 result->Draw("A*");
1896 result->GetXaxis()->SetTitle("threshold");
1897 result->GetYaxis()->SetTitle("integrated fractional rate above threshold");
1898
1899 canvas->SaveAs(Form("%s.gif", canvas->GetName()));
1900
1901 return result;
1902}
d1594f8a 1903
1904void AliHighMultiplicitySelector::MBComparison()
1905{
1906 //
1907 // finds the threshold from which onwards the number of found events above N times the mean
1908 // is higher using a high mult. trigger than just triggering with MB
1909 //
1910
1911 /*
1912
1913 gSystem->Load("libANALYSIS");
1914 gSystem->Load("libPWG0base");
1915 .L AliHighMultiplicitySelector.cxx+g
1916 x = new AliHighMultiplicitySelector();
1917 x->ReadHistograms("highmult_hijing100k.root");
1918 x->MBComparison();
1919
1920 */
1921
1922 // get x-sections
1923 TFile* file = TFile::Open("crosssectionEx.root");
1924 if (!file)
1925 return;
1926
1927 TH1* xSections[2];
1928 xSections[0] = dynamic_cast<TH1*> (gFile->Get("xSection2Ex"));
1929 xSections[1] = dynamic_cast<TH1*> (gFile->Get("xSection15Ex"));
1930
1931 // rate = L * sigma
1932 // sigma ~ 80 mb (Pythia 14 TeV)
1933 // 10^28 lum --> 8e2 Hz
1934 // 10^31 lum --> 8e5 Hz
1935 Int_t nRates = 4;
1936 Double_t rates[] = { 8e2, 8e3, 8e4, 8e5 };
1937
1938 // threshold in number of fired chips for corresponding rate
1939 //Int_t cuts[] = { 104, 134, 154, 170 }; // values for 20 Hz
1940 Int_t cuts[] = { 82, 124, 147, 164 }; // values for 50 Hz
1941
1942 // bandwidth, fractions (for MB, high mult.)
1943 Float_t bandwidth = 1e3;
1944 Float_t fractionMB = 0.5;
1945 Float_t fractionHM = 0.05;
1946
1947 // different limits to define "interesting events"
1948 Int_t nLimits = 9;
1949 Int_t limits[] = { 0, 1, 2, 4, 6, 7, 8, 9, 10 };
1950
1951 // put to 2 for second layer
1952 for (Int_t i=0; i<1; ++i)
1953 {
1954 if (!xSections[i])
1955 continue;
1956
1957 TH1* xSection = xSections[i];
1958 TH2* fMvsL = (i == 0) ? fMvsL1: fMvsL2;
1959
1960 // relative x-section, once we have a collision
1961 xSection->Scale(1.0 / xSection->Integral());
1962
1963 xSection->SetStats(kFALSE);
1964 xSection->SetTitle(""); //(i == 0) ? "SPD Layer 1" : "SPD Layer 2");
1965 xSection->GetXaxis()->SetTitle(Form("true multiplicity in |#eta| < %.1f", (i == 0) ? 2.0 : 1.5));
1966 xSection->GetXaxis()->SetRangeUser(0, (i == 0) ? 450 : 350);
1967 xSection->GetYaxis()->SetTitleOffset(1.2);
1968
1969 TCanvas* canvas = new TCanvas("MBComparison", "MBComparison", 1000, 800);
1970 canvas->Divide(3, 3);
1971
1972 for (Int_t currentLimit = 0; currentLimit<nLimits; currentLimit++)
1973 {
1974 // limit is N times the mean
1975 Int_t limit = (Int_t) (xSection->GetMean() * limits[currentLimit]);
1976 if (limit < 1)
1977 limit = 1;
1978
1979 TGraph* graphMB = new TGraph;
1980 graphMB->SetTitle(Form("Events with %d times above <n> (i.e. n >= %d)", limits[currentLimit], limit));
1981 graphMB->SetMarkerStyle(20);
1982
1983 TGraph* graphBoth = new TGraph;
1984 graphBoth->SetMarkerStyle(21);
1985
1986 Float_t min = bandwidth;
1987 Float_t max = 0;
1988
1989 for (Int_t current = 0; current<nRates; ++current)
1990 {
1991 Float_t rate = rates[current];
1992 Int_t cut = cuts[current];
1993
1994 TH1* triggerEff = (TH1*) GetTriggerEfficiency(fMvsL, cut)->Clone("triggerEff");
1995 TH1* proj = GetXSectionCut(xSection, fMvsL, cut);
1996
1997 Float_t downScaleMB1 = rate / bandwidth;
1998 if (downScaleMB1 < 1)
1999 downScaleMB1 = 1;
2000
2001 Float_t downScaleMB2 = rate / (bandwidth * fractionMB);
2002 if (downScaleMB2 < 1)
2003 downScaleMB2 = 1;
2004
2005 Float_t downScaleHM = rate * proj->Integral(1, xSection->GetNbinsX()) / (bandwidth * fractionHM);
2006 if (downScaleHM < 1)
2007 downScaleHM = 1;
2008
2009 Float_t rateMB1 = rate / downScaleMB1 * xSection->Integral(limit, xSection->GetNbinsX());
2010 Float_t rateMB2 = rate / downScaleMB2 * xSection->Integral(limit, xSection->GetNbinsX());
2011 Float_t rateHM = rate / downScaleHM * proj->Integral(limit, xSection->GetNbinsX());
2012 Float_t combinedRate = rateMB2 + rateHM;
2013
2014 graphMB->SetPoint(graphMB->GetN(), rate, rateMB1);
2015 graphBoth->SetPoint(graphBoth->GetN(), rate, combinedRate);
2016
2017 min = TMath::Min(min, TMath::Min(rateMB1, combinedRate));
2018 max = TMath::Max(min, TMath::Max(rateMB1, combinedRate));
2019
2020 Printf("The rates for events with %d times above <n> (i.e. n >= %d) at a rate of %.2e Hz is:", limits[currentLimit], limit, rate);
2021 Printf(" %.2e Hz in MB-only mode", rateMB1);
2022 Printf(" %.2e Hz = %.2e Hz + %.2e Hz in MB + high mult. mode", combinedRate, rateMB2, rateHM);
2023
2024 Printf(" The downscale factors are: %.2f %.2f %.2f", downScaleMB1, downScaleMB2, downScaleHM);
2025
2026 Int_t triggerLimit = 0;
2027 for (Int_t bin = 1; bin <= triggerEff->GetNbinsX(); bin++)
2028 if (triggerEff->GetBinContent(bin) < 0.5)
2029 triggerLimit = (Int_t) triggerEff->GetXaxis()->GetBinCenter(bin);
2030
2031 Printf(" Efficiency limit (50%%) is at multiplicity %d", triggerLimit);
144ff489 2032 Float_t fractionGood = proj->Integral(triggerLimit, proj->GetNbinsX()) / proj->Integral();
2033 Printf(" %.2f %% of the events are above the trigger limit", fractionGood * 100);
d1594f8a 2034
2035 if (triggerLimit > limit)
2036 Printf(" WARNING: interesting events also counted inside the trigger limit");
2037
2a311c4d 2038 Printf(" ");
d1594f8a 2039 }
2040
2041 canvas->cd(currentLimit+1)->SetLogx();
2042 canvas->cd(currentLimit+1)->SetLogy();
2043
2044 graphMB->Draw("AP");
2045 graphBoth->Draw("P SAME");
2046
2047 graphMB->GetYaxis()->SetRangeUser(0.5 * min, 2 * max);
2048 graphMB->GetXaxis()->SetTitle("Raw rate in Hz");
2049 graphMB->GetYaxis()->SetTitle("Event rate in Hz");
2050 }
2051 }
2052}