1 /*************************************************************************
2 * Copyright(c) 1998-2008, ALICE Experiment at CERN, All rights reserved. *
4 * Author: The ALICE Off-line Project. *
5 * Contributors are mentioned in the code where appropriate. *
7 * Permission to use, copy, modify and distribute this software and its *
8 * documentation strictly for non-commercial purposes is hereby granted *
9 * without fee, provided that the above copyright notice appears in all *
10 * copies and that both the copyright notice and this permission notice *
11 * appear in the supporting documentation. The authors make no claims *
12 * about the suitability of this software for any purpose. It is *
13 * provided "as is" without express or implied warranty. *
14 **************************************************************************/
16 /********************************
17 * estimating reference flow by *
18 * fitting q-distribution *
20 * author: Ante Bilandzic *
21 * (abilandzic@gmail.com) *
23 * based on the macro written *
24 * by Sergei Voloshin *
25 *******************************/
27 #define AliFlowAnalysisWithFittingQDistribution_cxx
29 #include "Riostream.h"
30 #include "AliFlowCommonConstants.h"
31 #include "AliFlowCommonHist.h"
32 #include "AliFlowCommonHistResults.h"
38 #include "TParticle.h"
40 #include "AliFlowEventSimple.h"
41 #include "AliFlowTrackSimple.h"
42 #include "AliFlowAnalysisWithFittingQDistribution.h"
56 //================================================================================================================
60 ClassImp(AliFlowAnalysisWithFittingQDistribution)
62 AliFlowAnalysisWithFittingQDistribution::AliFlowAnalysisWithFittingQDistribution():
64 fBookOnlyBasicCCH(kTRUE),
66 fCommonHistsResults(NULL),
81 fMultiplicityIs(AliFlowCommonConstants::kRP),
83 fUsePhiWeights(kFALSE),
84 fUsePtWeights(kFALSE),
85 fUseEtaWeights(kFALSE),
86 fUseParticleWeights(NULL),
90 fSumOfParticleWeights(NULL),
95 fStoreqDistributionVsMult(kFALSE),
96 fqDistributionVsMult(NULL),
100 fFittingParameters(NULL),
108 fFinalResultIsFromSigma2Fitted(kTRUE),
109 fPrintOnTheScreen(kTRUE),
115 // base list to hold all output objects:
116 fHistList = new TList();
117 fHistList->SetName("cobjFQD");
118 fHistList->SetOwner(kTRUE);
121 fAnalysisLabel = new TString();
123 // list to hold histograms with phi, pt and eta weights:
124 fWeightsList = new TList();
126 // initialize all arrays:
127 this->InitializeArrays();
129 } // end of constructor
131 //================================================================================================================
133 AliFlowAnalysisWithFittingQDistribution::~AliFlowAnalysisWithFittingQDistribution()
139 } // end of destructor
141 //================================================================================================================
144 void AliFlowAnalysisWithFittingQDistribution::Init()
146 // Access constants and book everything.
148 //save old value and prevent histograms from being added to directory
149 //to avoid name clashes in case multiple analaysis objects are used
151 Bool_t oldHistAddStatus = TH1::AddDirectoryStatus();
152 TH1::AddDirectory(kFALSE);
155 this->AccessConstants();
158 this->BookCommonHistograms();
159 this->BookAndFillWeightsHistograms();
160 this->BookEverythingForDistributions();
162 // store fitting parameters:
163 this->StoreFittingParameters();
166 fWeightsList->SetName("Weights");
167 fWeightsList->SetOwner(kTRUE);
168 fHistList->Add(fWeightsList);
170 // set harmonic in common control histograms (to be improved (should I do this somewhere else?)):
171 (fCommonHists->GetHarmonic())->Fill(0.5,fHarmonic);
174 TH1::AddDirectory(oldHistAddStatus);
175 } // end of void AliFlowAnalysisWithFittingQDistribution::Init()
177 //================================================================================================================
179 void AliFlowAnalysisWithFittingQDistribution::Make(AliFlowEventSimple* anEvent)
181 // Loop over data only in this method.
183 // a) Check all pointers used in this method;
184 // b) Fill the common control histograms;
185 // c) Loop over data and calculate Q-vector and sum of particle weights;
186 // d) Fill the histogram for q-distribution and sum of particle weights.
188 // a) Check all pointers used in this method:
189 this->CheckPointersUsedInMake();
191 // b) fill the common control histograms:
192 fCommonHists->FillControlHistograms(anEvent);
194 // c) Loop over data and fill histogram for q-distribution:
195 Double_t dPhi = 0.; // azimuthal angle in the laboratory frame
196 Double_t dPt = 0.; // transverse momentum
197 Double_t dEta = 0.; // pseudorapidity
198 Double_t wPhi = 1.; // phi weight
199 Double_t wPt = 1.; // pt weight
200 Double_t wEta = 1.; // eta weight
201 Double_t dReQ = 0.; // real part of Q-vector
202 Double_t dImQ = 0.; // imaginary part of Q-vector
203 Int_t nCounterNoRPs = 0; // needed only for shuffling
204 Int_t n = fHarmonic; // shortcut for the harmonic
205 Double_t dSumOfParticleWeights = 0.; // when particle weights are not used dSumOfParticleWeights is equal to multiplicity
206 AliFlowTrackSimple *aftsTrack = NULL;
207 Int_t nPrim = anEvent->NumberOfTracks(); // nPrim = total number of primary tracks
208 if(fExactNoRPs > 0 && anEvent->GetNumberOfRPs()<fExactNoRPs){return;} // shuffling
210 // Start loop over particles:
211 for(Int_t i=0;i<nPrim;i++)
213 if(fExactNoRPs > 0 && nCounterNoRPs>fExactNoRPs){continue;} // needed only for shuffling
214 aftsTrack=anEvent->GetTrack(i);
217 if(!(aftsTrack->InRPSelection())){continue;} // consider only tracks which are RPs
219 dPhi = aftsTrack->Phi();
220 dPt = aftsTrack->Pt();
221 dEta = aftsTrack->Eta();
222 if(fUsePhiWeights && fPhiWeights && fnBinsPhi) // determine phi weight for this particle:
224 wPhi = fPhiWeights->GetBinContent(1+(Int_t)(TMath::Floor(dPhi*fnBinsPhi/TMath::TwoPi())));
226 if(fUsePtWeights && fPtWeights && fPtBinWidth) // determine pt weight for this particle:
228 wPt = fPtWeights->GetBinContent(1+(Int_t)(TMath::Floor((dPt-fPtMin)/fPtBinWidth)));
230 if(fUseEtaWeights && fEtaWeights && fEtaBinWidth) // determine eta weight for this particle:
232 wEta = fEtaWeights->GetBinContent(1+(Int_t)(TMath::Floor((dEta-fEtaMin)/fEtaBinWidth)));
234 // Calculate real and imaginary part of Q-vector and sum of particle weights for this event:
236 dReQ += wPhi*wPt*wEta*TMath::Cos(n*dPhi);
237 dImQ += wPhi*wPt*wEta*TMath::Sin(n*dPhi);
238 // sum of particle weights:
239 dSumOfParticleWeights += wPhi*wPt*wEta; // when particle weights are not used this sum gives # of RPs, i.e. multiplicity
240 } // end of if(aftsTrack)
241 } // end of for(Int_t i=0;i<nPrim;i++)
243 // d) Fill the histogram for q-distribution and sum of particle weights:
244 Double_t q = 0.; // q = Q\sqrt{sum of particle weights}
245 if(dSumOfParticleWeights > 1.)
247 q = pow(dReQ*dReQ+dImQ*dImQ,0.5)/pow(dSumOfParticleWeights,0.5);
248 fqDistribution->Fill(q,1.);
249 fSumOfParticleWeights->Fill(dSumOfParticleWeights,1.);
250 if(fStoreqDistributionVsMult)
252 // Multiplicity bin of an event (relevant for all histos vs M):
253 Double_t dMultiplicityBin = 0.;
254 if(fMultiplicityIs==AliFlowCommonConstants::kRP)
256 Int_t nNumberOfRPsEBE = anEvent->GetNumberOfRPs(); // number of RPs (i.e. number of reference particles)
257 dMultiplicityBin = nNumberOfRPsEBE+0.5;
258 } else if(fMultiplicityIs==AliFlowCommonConstants::kExternal)
260 Int_t nReferenceMultiplicityEBE = anEvent->GetReferenceMultiplicity(); // reference multiplicity for current event
261 dMultiplicityBin = nReferenceMultiplicityEBE+0.5;
262 } else if(fMultiplicityIs==AliFlowCommonConstants::kPOI)
264 Int_t nNumberOfPOIsEBE = anEvent->GetNumberOfPOIs(); // number of POIs (i.e. number of particles of interest)
265 dMultiplicityBin = nNumberOfPOIsEBE+0.5;
268 fqDistributionVsMult->Fill(dMultiplicityBin,q);
269 } // end of if(fStoreqDistributionVsMult)
270 } // end of if(dSumOfParticleWeights > 1.)
274 //================================================================================================================
276 void AliFlowAnalysisWithFittingQDistribution::Finish(Bool_t doFit)
278 // Calculate the final results.
280 // a) Check all pointers used in this method;
281 // b) Acces common constants;
282 // c) Access fitting paremeters;
283 // d) Do the final fit of q-distribution;
284 // e) Fill common hist results;
285 // f) Print on the screen the final results.
287 // a) Check all pointers used in this method:
288 this->CheckPointersUsedInFinish();
290 // b) Access common constants:
291 this->AccessConstants();
293 // c) Access fitting paremeters:
294 this->AccessFittingParameters();
296 // d) Do the final fit of q-distribution:
299 this->DoFit(kFALSE); // sigma^2 not fitted (fixed to 0.5)
300 this->DoFit(kTRUE); // sigma^2 fitted
303 // e) Fill common hist results (by default fill with results obtained with sigma^2 fitted,
304 // alternatively use a setter SetFinalResultIsFromSigma2Fitted(kFALSE)):
305 this->FillCommonHistResults(fFinalResultIsFromSigma2Fitted);
307 // f) Print on the screen the final results:
308 if(fPrintOnTheScreen) this->PrintOnTheScreen();
310 } // end of void AliFlowAnalysisWithFittingQDistribution::Finish(Bool_t doFit)
312 //================================================================================================================
314 void AliFlowAnalysisWithFittingQDistribution::CheckPointersUsedInMake()
316 // Check all pointers used in method Make().
321 cout<<" WARNING (FQD::Make()): fCommonHists is NULL !!!!"<<endl;
328 cout<<" WARNING (FQD::Make()): fqDistribution is NULL !!!!"<<endl;
332 if(!fSumOfParticleWeights)
335 cout<<" WARNING (FQD::Make()): fSumOfParticleWeights is NULL !!!!"<<endl;
339 if(fUsePhiWeights && !fPhiWeights)
342 cout<<" WARNING (FQD::Make()): fPhiWeights is NULL !!!!"<<endl;
346 if(fUsePtWeights && !fPtWeights)
349 cout<<" WARNING (FQD::Make()): fPtWeights is NULL !!!!"<<endl;
353 if(fUseEtaWeights && !fEtaWeights)
356 cout<<" WARNING (FQD::Make()): fEtaWeights is NULL !!!!"<<endl;
361 } // end of void AliFlowAnalysisWithFittingQDistribution::CheckPointersUsedInMake()
363 //================================================================================================================
365 void AliFlowAnalysisWithFittingQDistribution::CheckPointersUsedInFinish()
367 // Check all pointers used in method Finish().
369 if(!fFittingParameters)
372 cout<<" WARNING (FQD::Finish()): fFittingParameters is NULL !!!!"<<endl;
379 cout<<" WARNING (FQD::Finish()): fqDistribution is NULL !!!!"<<endl;
383 if(!fSumOfParticleWeights)
386 cout<<" WARNING (FQD::Finish()): fSumOfParticleWeights is NULL !!!!"<<endl;
390 for(Int_t s2F=0;s2F<2;s2F++)
395 cout<<" WARNING (FQD::Finish()): "<<Form("fIntFlow[%d] is NULL !!!!",s2F)<<endl;
402 cout<<" WARNING (FQD::Finish()): "<<Form("fSigma2[%d] is NULL !!!!",s2F)<<endl;
409 cout<<" WARNING (FQD::Finish()): "<<Form("fChi2[%d] is NULL !!!!",s2F)<<endl;
413 } // end of for(Int_t s2F=0;s2F<2;s2F++)
414 if(!fCommonHistsResults)
417 cout<<"WARNING (FQD::Finish()): fCommonHistsResults is NULL !!!!"<<endl;
424 cout<<"WARNING (FQD::Finish()): fCommonHists is NULL !!!!"<<endl;
429 } // end of void AliFlowAnalysisWithFittingQDistribution::CheckPointersUsedInFinish()
431 //================================================================================================================
433 void AliFlowAnalysisWithFittingQDistribution::GetOutputHistograms(TList *outputListHistos)
435 // Get pointers to all output histograms (called before Finish()).
439 // 1.) common control histograms and common histograms for final results:
440 TString commonHistName = "AliFlowCommonHistFQD";
441 commonHistName += fAnalysisLabel->Data();
442 AliFlowCommonHist *commonHist = dynamic_cast<AliFlowCommonHist*>(outputListHistos->FindObject(commonHistName.Data()));
443 if(commonHist) this->SetCommonHists(commonHist);
445 TString commonHistResName = "AliFlowCommonHistResultsFQD";
446 commonHistResName += fAnalysisLabel->Data();
447 AliFlowCommonHistResults *commonHistRes = dynamic_cast<AliFlowCommonHistResults*>
448 (outputListHistos->FindObject(commonHistResName.Data()));
449 if(commonHistRes) this->SetCommonHistsResults(commonHistRes);
452 TList *weightsList = dynamic_cast<TList*>(outputListHistos->FindObject("Weights"));
453 if(weightsList){this->SetWeightsList(weightsList);}
454 Bool_t bUsePhiWeights = kFALSE;
455 Bool_t bUsePtWeights = kFALSE;
456 Bool_t bUseEtaWeights = kFALSE;
457 TString fUseParticleWeightsName = "fUseParticleWeightsFQD";
458 fUseParticleWeightsName += fAnalysisLabel->Data();
459 TProfile *useParticleWeights = NULL;
462 useParticleWeights = dynamic_cast<TProfile*>(weightsList->FindObject(fUseParticleWeightsName.Data()));
464 if(useParticleWeights)
466 this->SetUseParticleWeights(useParticleWeights);
467 bUsePhiWeights = (Int_t)useParticleWeights->GetBinContent(1);
468 this->SetUsePhiWeights(bUsePhiWeights);
469 bUsePtWeights = (Int_t)useParticleWeights->GetBinContent(2);
470 this->SetUsePtWeights(bUsePtWeights);
471 bUseEtaWeights = (Int_t)useParticleWeights->GetBinContent(3);
472 this->SetUseEtaWeights(bUseEtaWeights);
475 // 3.) distributions and 4.) final results of fitting:
476 TString sigmaFlag[2] = {"#sigma^{2} not fitted","#sigma^{2} fitted"};
478 TString qDistributionName = "fqDistribution";
479 qDistributionName += fAnalysisLabel->Data();
480 // sum of particle weights:
481 TString sumOfParticleWeightsName = "fSumOfParticleWeights";
482 sumOfParticleWeightsName += fAnalysisLabel->Data();
483 // final results for reference flow:
484 TString intFlowName = "fIntFlowFQD";
485 intFlowName += fAnalysisLabel->Data();
487 TString sigma2Name = "fSigma2";
488 sigma2Name += fAnalysisLabel->Data();
490 TString chi2Name = "fChi2";
491 chi2Name += fAnalysisLabel->Data();
493 TString fittingFunctionName = "fFittingFunction";
494 fittingFunctionName += fAnalysisLabel->Data();
496 TH1D *qDistribution = NULL;
497 TH1D *sumOfParticleWeights = NULL;
498 TH1D *intFlow[2] = {NULL};
499 TH1D *sigma2[2] = {NULL};
500 TH1D *chi2[2] = {NULL};
501 TF1 *fittingFunction[2] = {NULL};
504 qDistribution = dynamic_cast<TH1D*>(outputListHistos->FindObject(Form("%s",qDistributionName.Data())));
507 this->SetqDistribution(qDistribution);
510 cout<<"WARNING: qDistribution is NULL in AFAWFQD::GOH() !!!!"<<endl;
512 // sum of particle weights:
513 sumOfParticleWeights = dynamic_cast<TH1D*>(outputListHistos->FindObject(Form("%s",sumOfParticleWeightsName.Data())));
514 if(sumOfParticleWeights)
516 this->SetSumOfParticleWeights(sumOfParticleWeights);
519 cout<<"WARNING: sumOfParticleWeights is NULL in AFAWFQD::GOH() !!!!"<<endl;
522 for(Int_t f=0;f<2;f++)
524 // final results for reference flow:
525 intFlow[f] = dynamic_cast<TH1D*>(outputListHistos->FindObject(Form("%s, %s",intFlowName.Data(),sigmaFlag[f].Data())));
528 this->SetIntFlow(intFlow[f],f);
531 cout<<"WARNING: intFlow[f] is NULL in AFAWFQD::GOH() !!!!"<<endl;
532 cout<<"f = "<<f<<endl;
535 sigma2[f] = dynamic_cast<TH1D*>(outputListHistos->FindObject(Form("%s, %s",sigma2Name.Data(),sigmaFlag[f].Data())));
538 this->SetSigma2(sigma2[f],f);
541 cout<<"WARNING: sigma2[f] is NULL in AFAWFQD::GOH() !!!!"<<endl;
542 cout<<"f = "<<f<<endl;
545 chi2[f] = dynamic_cast<TH1D*>(outputListHistos->FindObject(Form("%s, %s",chi2Name.Data(),sigmaFlag[f].Data())));
548 this->SetChi2(chi2[f],f);
551 cout<<"WARNING: chi2[f] is NULL in AFAWFQD::GOH() !!!!"<<endl;
552 cout<<"f = "<<f<<endl;
554 // fitting functions:
555 fittingFunction[f] = dynamic_cast<TF1*>(outputListHistos->FindObject(Form("%s, %s",fittingFunctionName.Data(),sigmaFlag[f].Data())));
556 if(fittingFunction[f])
558 this->SetFittingFunction(fittingFunction[f],f);
561 cout<<"WARNING: fittingFunction[f] is NULL in AFAWFQD::GOH() !!!!"<<endl;
562 cout<<"f = "<<f<<endl;
564 } // end of for(Int_t f=0;f<2;f++)
566 // 5.) fitting parameters:
568 TString fittingParametersName = "fFittingParameters";
569 fittingParametersName += fAnalysisLabel->Data();
570 TProfile *fittingParameters = NULL;
571 fittingParameters = dynamic_cast<TProfile*>(outputListHistos->FindObject(fittingParametersName.Data()));
572 if(fittingParameters)
574 this->SetFittingParameters(fittingParameters);
577 cout<<"WARNING:fittingParameters is NULL in AFAWFQD::GOH() !!!!"<<endl;
580 } else // to if(outputListHistos)
582 cout<<"WARNING: outputListHistos is NULL in AFAWFQD::GOH() !!!!"<<endl;
586 } // end of void AliFlowAnalysisWithFittingQDistribution::GetOutputHistograms(TList *outputListHistos)
588 //================================================================================================================
590 void AliFlowAnalysisWithFittingQDistribution::WriteHistograms(TString* outputFileName)
592 //store the final results in output .root file
593 TFile *output = new TFile(outputFileName->Data(),"RECREATE");
594 //output->WriteObject(fHistList, "cobjFQD","SingleKey");
595 fHistList->SetName("cobjFQD");
596 fHistList->SetOwner(kTRUE);
597 fHistList->Write(fHistList->GetName(), TObject::kSingleKey);
601 //================================================================================================================
603 void AliFlowAnalysisWithFittingQDistribution::WriteHistograms(TString outputFileName)
605 //store the final results in output .root file
606 TFile *output = new TFile(outputFileName.Data(),"RECREATE");
607 //output->WriteObject(fHistList, "cobjFQD","SingleKey");
608 fHistList->SetName("cobjFQD");
609 fHistList->SetOwner(kTRUE);
610 fHistList->Write(fHistList->GetName(), TObject::kSingleKey);
614 //================================================================================================================
616 void AliFlowAnalysisWithFittingQDistribution::WriteHistograms(TDirectoryFile *outputFileName)
618 //store the final results in output .root file
619 fHistList->SetName("cobjFQD");
620 fHistList->SetOwner(kTRUE);
621 outputFileName->Add(fHistList);
622 outputFileName->Write(outputFileName->GetName(), TObject::kSingleKey);
625 //================================================================================================================
627 void AliFlowAnalysisWithFittingQDistribution::InitializeArrays()
629 // Initialize all arrays.
631 for(Int_t s2F=0;s2F<2;s2F++) // sigma^2 not fitted (0) or fitted (1)
633 fIntFlow[s2F] = NULL;
636 fFittingFunction[s2F] = NULL;
639 } // end of void AliFlowAnalysisWithFittingQDistribution::InitializeArrays()
641 //================================================================================================================
643 void AliFlowAnalysisWithFittingQDistribution::BookCommonHistograms()
645 // Book common histograms.
647 // common control histogram:
648 TString commonHistName = "AliFlowCommonHistFQD";
649 commonHistName += fAnalysisLabel->Data();
650 fCommonHists = new AliFlowCommonHist(commonHistName.Data(),commonHistName.Data(),fBookOnlyBasicCCH);
651 fHistList->Add(fCommonHists);
653 // common histograms for final results:
654 TString commonHistResName = "AliFlowCommonHistResultsFQD";
655 commonHistResName += fAnalysisLabel->Data();
656 fCommonHistsResults = new AliFlowCommonHistResults(commonHistResName.Data(),"",fHarmonic);
657 fHistList->Add(fCommonHistsResults);
659 } // end of void AliFlowAnalysisWithFittingQDistribution::BookCommonHistograms()
661 //================================================================================================================
663 void AliFlowAnalysisWithFittingQDistribution::BookAndFillWeightsHistograms()
665 // Book and fill histograms which hold phi, pt and eta weights.
669 cout<<"WARNING: fWeightsList is NULL in AFAWFQD::BAFWH() !!!!"<<endl;
673 TString fUseParticleWeightsName = "fUseParticleWeightsFQD";
674 fUseParticleWeightsName += fAnalysisLabel->Data();
675 fUseParticleWeights = new TProfile(fUseParticleWeightsName.Data(),"0 = particle weight not used, 1 = particle weight used ",3,0,3);
676 fUseParticleWeights->SetLabelSize(0.08);
677 (fUseParticleWeights->GetXaxis())->SetBinLabel(1,"w_{#phi}");
678 (fUseParticleWeights->GetXaxis())->SetBinLabel(2,"w_{p_{T}}");
679 (fUseParticleWeights->GetXaxis())->SetBinLabel(3,"w_{#eta}");
680 fUseParticleWeights->Fill(0.5,(Int_t)fUsePhiWeights);
681 fUseParticleWeights->Fill(1.5,(Int_t)fUsePtWeights);
682 fUseParticleWeights->Fill(2.5,(Int_t)fUseEtaWeights);
683 fWeightsList->Add(fUseParticleWeights);
687 if(fWeightsList->FindObject("phi_weights"))
689 fPhiWeights = dynamic_cast<TH1F*>(fWeightsList->FindObject("phi_weights"));
690 if(!fPhiWeights){printf("\n WARNING (FQD): !fPhiWeights !!!!\n");exit(0);}
691 if(TMath::Abs(fPhiWeights->GetBinWidth(1)-fPhiBinWidth)>pow(10.,-6.))
694 cout<<"WARNING (FQD): Inconsistent binning in histograms for phi-weights throughout the code."<<endl;
700 cout<<"WARNING: fWeightsList->FindObject(\"phi_weights\") is NULL in AFAWFQD::BAFWH() !!!!"<<endl;
703 } // end of if(fUsePhiWeights)
707 if(fWeightsList->FindObject("pt_weights"))
709 fPtWeights = dynamic_cast<TH1D*>(fWeightsList->FindObject("pt_weights"));
710 if(!fPtWeights){printf("\n WARNING (FQD): !fPtWeights !!!!\n");exit(0);}
711 if(TMath::Abs(fPtWeights->GetBinWidth(1)-fPtBinWidth)>pow(10.,-6.))
714 cout<<"WARNING (FQD): Inconsistent binning in histograms for pt-weights throughout the code."<<endl;
720 cout<<"WARNING: fWeightsList->FindObject(\"pt_weights\") is NULL in AFAWFQD::BAFWH() !!!!"<<endl;
723 } // end of if(fUsePtWeights)
727 if(fWeightsList->FindObject("eta_weights"))
729 fEtaWeights = dynamic_cast<TH1D*>(fWeightsList->FindObject("eta_weights"));
730 if(!fEtaWeights){printf("\n WARNING (FQD): !fEtaWeights !!!!\n");exit(0);}
731 if(TMath::Abs(fEtaWeights->GetBinWidth(1)-fEtaBinWidth)>pow(10.,-6.))
734 cout<<"WARNING (FQD): Inconsistent binning in histograms for eta-weights throughout the code."<<endl;
740 cout<<"WARNING: fUseEtaWeights && fWeightsList->FindObject(\"eta_weights\") is NULL in AFAWFQD::BAFWH() !!!!"<<endl;
743 } // end of if(fUseEtaWeights)
745 } // end of AliFlowAnalysisWithFittingQDistribution::BookAndFillWeightsHistograms()
747 //================================================================================================================================
749 void AliFlowAnalysisWithFittingQDistribution::AccessConstants()
751 // access needed common constants from AliFlowCommonConstants
753 fnBinsPhi = AliFlowCommonConstants::GetMaster()->GetNbinsPhi();
754 fPhiMin = AliFlowCommonConstants::GetMaster()->GetPhiMin();
755 fPhiMax = AliFlowCommonConstants::GetMaster()->GetPhiMax();
756 if(fnBinsPhi) fPhiBinWidth = (fPhiMax-fPhiMin)/fnBinsPhi;
757 fnBinsPt = AliFlowCommonConstants::GetMaster()->GetNbinsPt();
758 fPtMin = AliFlowCommonConstants::GetMaster()->GetPtMin();
759 fPtMax = AliFlowCommonConstants::GetMaster()->GetPtMax();
760 if(fnBinsPt) fPtBinWidth = (fPtMax-fPtMin)/fnBinsPt;
761 fnBinsEta = AliFlowCommonConstants::GetMaster()->GetNbinsEta();
762 fEtaMin = AliFlowCommonConstants::GetMaster()->GetEtaMin();
763 fEtaMax = AliFlowCommonConstants::GetMaster()->GetEtaMax();
764 if(fnBinsEta) fEtaBinWidth = (fEtaMax-fEtaMin)/fnBinsEta;
766 } // end of void AliFlowAnalysisWithFittingQDistribution::AccessConstants()
768 //================================================================================================================================
770 void AliFlowAnalysisWithFittingQDistribution::BookEverythingForDistributions()
772 // Book all objects relevant for fitting of q-distributions.
775 TString sigmaFlag[2] = {"#sigma^{2} not fitted","#sigma^{2} fitted"};
777 TString fqDistributionName = "fqDistribution";
778 fqDistributionName += fAnalysisLabel->Data();
779 fqDistribution = new TH1D(Form("%s",fqDistributionName.Data()),"q-distribution",fqNbins,fqMin,fqMax);
780 fqDistribution->SetXTitle(Form("q_{%d}=|Q_{%d}|/#sqrt{M}",fHarmonic,fHarmonic));
781 fqDistribution->SetYTitle("Counts");
782 fHistList->Add(fqDistribution);
783 // q-distribution vs multiplicity:
784 if(fStoreqDistributionVsMult)
786 TString fqDistributionVsMultName = "fqDistributionVsMult";
787 fqDistributionVsMultName += fAnalysisLabel->Data();
788 fqDistributionVsMult = new TH2D(Form("%s",fqDistributionVsMultName.Data()),"q-distribution vs M",fnBinsMult,fMinMult,fMaxMult,fqNbins,fqMin,fqMax);
789 fqDistributionVsMult->GetYaxis()->SetTitle(Form("q_{%d}=|Q_{%d}|/#sqrt{M}",fHarmonic,fHarmonic));
790 if(fMultiplicityIs==AliFlowCommonConstants::kRP)
792 fqDistributionVsMult->GetXaxis()->SetTitle("# RPs");
793 } else if(fMultiplicityIs==AliFlowCommonConstants::kExternal)
795 fqDistributionVsMult->GetXaxis()->SetTitle("Reference multiplicity (from ESD)");
796 } else if(fMultiplicityIs==AliFlowCommonConstants::kPOI)
798 fqDistributionVsMult->GetXaxis()->SetTitle("# POIs");
800 fHistList->Add(fqDistributionVsMult);
801 } // end of if(fStoreqDistributionVsMult)
802 // Sum of particle weights:
803 TString fSumOfParticleWeightsName = "fSumOfParticleWeights";
804 fSumOfParticleWeightsName += fAnalysisLabel->Data();
805 fSumOfParticleWeights = new TH1D(Form("%s",fSumOfParticleWeightsName.Data()),"Sum of particle weights",10000,0,100000); // (to be improved - harwired limits and number of bins)
806 fSumOfParticleWeights->SetXTitle("#sum_{i=1}^{N} w_{i}");
807 fSumOfParticleWeights->GetXaxis()->SetTitleSize(0.03);
808 fSumOfParticleWeights->SetYTitle("Counts");
809 fHistList->Add(fSumOfParticleWeights);
810 // Final results for integrated flow:
811 TString fIntFlowName = "fIntFlowFQD";
812 fIntFlowName += fAnalysisLabel->Data();
814 TString fSigma2Name = "fSigma2";
815 fSigma2Name += fAnalysisLabel->Data();
817 TString fChi2Name = "fChi2";
818 fChi2Name += fAnalysisLabel->Data();
820 TString fittingFunctionName = "fFittingFunction";
821 fittingFunctionName += fAnalysisLabel->Data();
823 for(Int_t f=0;f<2;f++) // sigma^2 not fitted (0) or fitted (1)
825 // final results for integrated flow:
826 fIntFlow[f] = new TH1D(Form("%s, %s",fIntFlowName.Data(),sigmaFlag[f].Data()),Form("Reference Flow (%s)",sigmaFlag[f].Data()),1,0,1);
827 fIntFlow[f]->SetLabelSize(0.08);
828 fHistList->Add(fIntFlow[f]);
830 fSigma2[f] = new TH1D(Form("%s, %s",fSigma2Name.Data(),sigmaFlag[f].Data()),Form("#sigma^{2} (%s)",sigmaFlag[f].Data()),1,0,1);
831 fSigma2[f]->SetLabelSize(0.08);
832 (fSigma2[f]->GetXaxis())->SetBinLabel(1,"#sigma^{2}");
833 fHistList->Add(fSigma2[f]);
835 fChi2[f] = new TH1D(Form("%s, %s",fChi2Name.Data(),sigmaFlag[f].Data()),Form("#chi^{2} (%s)",sigmaFlag[f].Data()),1,0,1);
836 fChi2[f]->SetLabelSize(0.08);
837 (fChi2[f]->GetXaxis())->SetLabelOffset(0.01);
838 (fChi2[f]->GetXaxis())->SetBinLabel(1,"#chi^{2}");
839 fHistList->Add(fChi2[f]);
840 // fitting functions:
841 fFittingFunction[f] = new TF1(Form("%s, %s",fittingFunctionName.Data(),sigmaFlag[f].Data()),"[2]*(x/[1])*exp(-(x*x+[0]*[0])/(2.*[1]))*TMath::BesselI0(x*[0]/[1])");
842 fHistList->Add(fFittingFunction[f]);
843 } // end of for(Int_t f=0;f<2;f++) // sigma^2 not fitted or fitted
844 // Book profile fFittingParameters which will hold all fitting parameters:
845 TString fFittingParametersName = "fFittingParameters";
846 fFittingParametersName += fAnalysisLabel->Data();
847 fFittingParameters = new TProfile(fFittingParametersName.Data(),"Parameters for fitting q-distribution",13,0,13);
848 fFittingParameters->SetLabelSize(0.05);
849 fFittingParameters->GetXaxis()->SetBinLabel(1,"treshold");
850 fFittingParameters->GetXaxis()->SetBinLabel(2,Form("starting v_{%d}",fHarmonic));
851 fFittingParameters->GetXaxis()->SetBinLabel(3,Form("min. v_{%d}",fHarmonic));
852 fFittingParameters->GetXaxis()->SetBinLabel(4,Form("max. v_{%d}",fHarmonic));
853 fFittingParameters->GetXaxis()->SetBinLabel(5,"starting #sigma^{2}");
854 fFittingParameters->GetXaxis()->SetBinLabel(6,"min. #sigma^{2}");
855 fFittingParameters->GetXaxis()->SetBinLabel(7,"max. #sigma^{2}");
856 fFittingParameters->GetXaxis()->SetBinLabel(8,"Final result is from #sigma^{2} fitted?");
857 fFittingParameters->GetXaxis()->SetBinLabel(9,"Print results on the screen?");
858 fFittingParameters->GetXaxis()->SetBinLabel(10,"fStoreqDistributionVsMult");
859 fFittingParameters->GetXaxis()->SetBinLabel(11,"fMultiplicityIs");
860 fFittingParameters->GetXaxis()->SetBinLabel(12,"fDoFit");
861 fFittingParameters->GetXaxis()->SetBinLabel(13,"fExactNoRPs");
862 fHistList->Add(fFittingParameters);
864 } // end of void AliFlowAnalysisWithFittingQDistribution::BookEverythingForDistributions()
866 //================================================================================================================================
868 void AliFlowAnalysisWithFittingQDistribution::DoFit(Bool_t sigma2Fitted)
870 // Do the final fit of q-distribution.
872 Int_t s2F = (Int_t)(sigma2Fitted); // shortcut
873 Double_t AvM = fSumOfParticleWeights->GetMean(1); // average multiplicity
874 //Int_t nEvts = (Int_t)fSumOfParticleWeights->GetEntries(); // number of events:
876 // Start fitting from the bin with at least fTreshold entries,
877 // finish fitting at the bin with at least fTreshold entries:
878 Int_t binMin = fqDistribution->FindFirstBinAbove(fTreshold);
879 Int_t binMax = fqDistribution->FindLastBinAbove(fTreshold);
880 Double_t binWidth = fqDistribution->GetBinWidth(4); // assuming that all bins have the same width
881 if(TMath::Abs(binWidth) < 1.e-44)
884 cout<<"WARNING (FQD): binWidth == 0 in AFAWFQD::DoFit()"<<endl;
888 Double_t qmin = (binMin-1)*binWidth;
889 Double_t qmax = (binMax)*binWidth;
890 Double_t ent = 0.; // number of entries between binMin and binMax:
891 for(Int_t b=binMin;b<=binMax;b++)
893 ent += fqDistribution->GetBinContent(b);
896 Double_t norm = binWidth*ent; // norm (assuming that all bins have the same width)
898 fFittingFunction[s2F]->SetRange(qmin,qmax);
899 fFittingFunction[s2F]->SetParNames("v*sqrt{sum of particle weights}","sigma^2","norm");
900 fFittingFunction[s2F]->SetParameters(fvStart*pow(AvM,0.5),fSigma2Start,norm);
901 fFittingFunction[s2F]->SetParLimits(0,fvMin*pow(AvM,0.5),fvMax*pow(AvM,0.5));
904 fFittingFunction[s2F]->FixParameter(1,0.5);
907 fFittingFunction[s2F]->SetParLimits(1,fSigma2Min,fSigma2Max);
909 fFittingFunction[s2F]->FixParameter(2,norm);
910 // Fitting is done here:
911 // Remark: do fit only if # of entries > 50 - this is only a pragmatics fix to avoid TMinuit crash (to be improved)
914 fqDistribution->Fit(fFittingFunction[s2F]->GetName(),"NQ","",qmin,qmax);
918 Double_t v = 0.; // reference flow
919 Double_t vError = 0.; // error of reference flow
920 Double_t sigma2 = 0.; // sigma^2
921 Double_t sigma2Error = 0.; // error of sigma^2
922 Double_t chi2 = 0; // chi^2 from Minuit
926 v = fFittingFunction[s2F]->GetParameter(0)/pow(AvM,0.5);
927 vError = fFittingFunction[s2F]->GetParError(0)/pow(AvM,0.5);
928 fIntFlow[s2F]->SetBinContent(1,v); // s2F is shortcut for "sigma^2 fitted"
929 fIntFlow[s2F]->SetBinError(1,vError); // s2F is shortcut for "sigma^2 fitted"
933 cout<<"WARNING (FQD): AvM == 0 in AFAWFQD::DoFit()"<<endl;
937 if(s2F == 0) // sigma^2 not fitted, but fixed to 0.5
940 fSigma2[0]->SetBinContent(1,sigma2);
941 fSigma2[0]->SetBinError(1,0.);
942 } else // sigma^2 fitted
944 sigma2 = fFittingFunction[s2F]->GetParameter(1);
945 sigma2Error = fFittingFunction[s2F]->GetParError(1);
946 fSigma2[1]->SetBinContent(1,sigma2);
947 fSigma2[1]->SetBinError(1,sigma2Error);
950 chi2 = fFittingFunction[s2F]->GetChisquare();
951 fChi2[s2F]->SetBinContent(1,chi2);
953 } // end of void AliFlowAnalysisWithFittingQDistribution::DoFit()
955 //================================================================================================================================
957 void AliFlowAnalysisWithFittingQDistribution::FillCommonHistResults(Bool_t sigma2Fitted)
959 // Fill common result histogram for reference flow and resolution.
961 // Remark: by default the result obtained with sigma^2 fitted is being stored.
962 // In order to store the result obtained with sigma^2 fixed use a setter SetFinalResultIsFromSigma2Fitted(kFALSE).
964 Int_t s2F = (Int_t)sigma2Fitted; // shortcut
967 Double_t v = fIntFlow[s2F]->GetBinContent(1);
968 Double_t vError = fIntFlow[s2F]->GetBinError(1);
969 fCommonHistsResults->FillIntegratedFlow(v,vError);
971 Double_t AvM = fSumOfParticleWeights->GetMean(1);
972 Double_t chi2 = AvM*pow(v,2.); // chi^2
975 fCommonHistsResults->FillChi(pow(chi2,0.5));
978 } // end of void AliFlowAnalysisWithFittingQDistribution::FillCommonHistResultsIntFlow(Bool_t useParticleWeights, Bool_t sigma2NotFixed)
980 //================================================================================================================================
982 void AliFlowAnalysisWithFittingQDistribution::PrintOnTheScreen()
984 // Print the final results on the screen.
986 // shortcut for the harmonic:
988 if(fCommonHists->GetHarmonic())
990 n = (Int_t)(fCommonHists->GetHarmonic())->GetBinContent(1);
995 cout<<"***************************************"<<endl;
996 cout<<"***************************************"<<endl;
997 cout<<" reference flow by fitting "<<endl;
998 cout<<" q-distribution: "<<endl;
999 if(fUsePhiWeights||fUsePtWeights||fUseEtaWeights)
1001 cout<<" (with weights) "<<endl;
1004 cout<<" (without weights) "<<endl;
1007 cout<<"1.) sigma^2 not fitted: "<<endl;
1008 cout<<" v_"<<n<<"{FQD} = "<<fIntFlow[0]->GetBinContent(1)<<" +/- "<<fIntFlow[0]->GetBinError(1)<<endl;
1009 cout<<" sigma^2 = 0.5 +/- 0 "<<endl;
1010 cout<<" chi^2 = "<<fChi2[0]->GetBinContent(1)<<" (Minuit)"<<endl;
1012 if(TMath::Abs(fIntFlow[0]->GetBinContent(1)-fvMin)<1.e-10 ||
1013 TMath::Abs(fIntFlow[0]->GetBinContent(1)-fvMax)<1.e-10)
1015 cout<<" WARNING: value of v_"<<n<<"{FQD}"<<" is on the boundary"<<endl;
1016 cout<<" of fitting interval. Redo the fit."<< endl;
1019 cout<<"2.) sigma^2 fitted: "<<endl;
1020 cout<<" v_"<<n<<"{FQD} = "<<fIntFlow[1]->GetBinContent(1)<<" +/- "<<fIntFlow[1]->GetBinError(1)<<endl;
1021 cout<<" sigma^2 = "<<fSigma2[1]->GetBinContent(1)<<" +/- "<<fSigma2[1]->GetBinError(1)<<endl;
1022 cout<<" chi^2 = "<<fChi2[1]->GetBinContent(1)<<" (Minuit)"<<endl;
1024 if(TMath::Abs(fIntFlow[0]->GetBinContent(1)-fvMin)<1.e-10 ||
1025 TMath::Abs(fIntFlow[0]->GetBinContent(1)-fvMax)<1.e-10)
1027 cout<<" WARNING: value of v_"<<n<<"{FQD}"<<" is on the boundary"<<endl;
1028 cout<<" of fitting interval. Redo the fit."<< endl;
1031 if(TMath::Abs(fSigma2[1]->GetBinContent(1)-fSigma2Min)<1.e-10 ||
1032 TMath::Abs(fSigma2[1]->GetBinContent(1)-fSigma2Max)<1.e-10)
1034 cout<<" WARNING: value of sigma^2 is on the boundary"<<endl;
1035 cout<<" of fitting interval. Redo the fit."<< endl;
1038 cout<<" nEvts = "<<fSumOfParticleWeights->GetEntries()<<", AvM = "<<fSumOfParticleWeights->GetMean()<<endl;
1040 cout<<"***************************************"<<endl;
1041 cout<<"***************************************"<<endl;
1044 } // end of void AliFlowAnalysisWithFittingQDistribution::PrintOnTheScreen()
1046 //================================================================================================================================
1048 void AliFlowAnalysisWithFittingQDistribution::StoreFittingParameters()
1050 // Store fitting parameters for the fit of q-distribution in profile fFittingParameters.
1052 if(!fFittingParameters)
1055 cout<<"WARNING (FQD): fFittingParameters is NULL in AFAWFQD::SFP() !!!!"<<endl;
1059 fFittingParameters->Reset();
1060 fFittingParameters->Fill(0.5,fTreshold);
1061 fFittingParameters->Fill(1.5,fvStart);
1062 fFittingParameters->Fill(2.5,fvMin);
1063 fFittingParameters->Fill(3.5,fvMax);
1064 fFittingParameters->Fill(4.5,fSigma2Start);
1065 fFittingParameters->Fill(5.5,fSigma2Min);
1066 fFittingParameters->Fill(6.5,fSigma2Max);
1067 fFittingParameters->Fill(7.5,fFinalResultIsFromSigma2Fitted);
1068 fFittingParameters->Fill(8.5,fPrintOnTheScreen);
1069 fFittingParameters->Fill(9.5,fStoreqDistributionVsMult);
1070 // which multiplicity was used:
1071 if(fMultiplicityIs==AliFlowCommonConstants::kRP) // # of Reference Particles
1073 fFittingParameters->Fill(10.5,0); // 0 = # of Reference Particles
1074 } else if(fMultiplicityIs==AliFlowCommonConstants::kExternal)
1076 fFittingParameters->Fill(10.5,1); // 1 = ref. mult. from ESD
1077 } else if(fMultiplicityIs==AliFlowCommonConstants::kPOI)
1079 fFittingParameters->Fill(10.5,2); // 2 = # of Particles of Interest
1081 fFittingParameters->Fill(11.5,fDoFit);
1082 fFittingParameters->Fill(12.5,fExactNoRPs);
1084 } // end of void AliFlowAnalysisWithFittingQDistribution::StoreFittingParameters()
1086 //================================================================================================================================
1088 void AliFlowAnalysisWithFittingQDistribution::AccessFittingParameters()
1090 // Access fitting parameters for the fit of q-distribution.
1092 fTreshold = fFittingParameters->GetBinContent(1);
1093 fvStart = fFittingParameters->GetBinContent(2);
1094 fvMin = fFittingParameters->GetBinContent(3);
1095 fvMax = fFittingParameters->GetBinContent(4);
1096 fSigma2Start = fFittingParameters->GetBinContent(5);
1097 fSigma2Min = fFittingParameters->GetBinContent(6);
1098 fSigma2Max = fFittingParameters->GetBinContent(7);
1099 fFinalResultIsFromSigma2Fitted = (Bool_t)fFittingParameters->GetBinContent(8);
1100 fPrintOnTheScreen = (Bool_t)fFittingParameters->GetBinContent(9);
1101 fStoreqDistributionVsMult = (Bool_t)fFittingParameters->GetBinContent(10);
1102 fDoFit = (Bool_t)fFittingParameters->GetBinContent(12);
1103 fExactNoRPs = (Int_t)fFittingParameters->GetBinContent(13);
1105 } // end of void AliFlowAnalysisWithFittingQDistribution::AccessFittingParameters()