laura is hosted by Hepforge, IPPP Durham
Laura++  v3r5
A maximum likelihood fitting package for performing Dalitz-plot analysis.
LauEffModel.cc
Go to the documentation of this file.
1 
2 /*
3 Copyright 2004 University of Warwick
4 
5 Licensed under the Apache License, Version 2.0 (the "License");
6 you may not use this file except in compliance with the License.
7 You may obtain a copy of the License at
8 
9  http://www.apache.org/licenses/LICENSE-2.0
10 
11 Unless required by applicable law or agreed to in writing, software
12 distributed under the License is distributed on an "AS IS" BASIS,
13 WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 See the License for the specific language governing permissions and
15 limitations under the License.
16 */
17 
18 /*
19 Laura++ package authors:
20 John Back
21 Paul Harrison
22 Thomas Latham
23 */
24 
29 #include <cstdlib>
30 #include <iostream>
31 
32 #include "TSystem.h"
33 #include "Lau2DHistDP.hh"
34 #include "Lau2DSplineDP.hh"
35 #include "LauDaughters.hh"
36 #include "LauEffModel.hh"
37 #include "LauKinematics.hh"
38 #include "LauVetoes.hh"
39 
41 
42 
43 LauEffModel::LauEffModel(const LauDaughters* daughters, const LauVetoes* vetoes) :
44  daughters_( daughters ),
45  vetoes_( vetoes ),
46  effHisto_( 0 ),
47  fluctuateEffHisto_( kFALSE ),
48  lowBinWarningIssued_( kFALSE ),
49  highBinWarningIssued_( kFALSE )
50 {
51  if ( daughters_ == 0 ) {
52  std::cerr << "ERROR in LauEffModel Constructor : invalid pointer to daughters object supplied." << std::endl;
53  gSystem->Exit(EXIT_FAILURE);
54  }
55 }
56 
58 {
59  std::vector<Lau2DAbsDP*>::iterator it = effHisto_.begin();
60  std::vector<Lau2DAbsDP*>::iterator end = effHisto_.end();
61  for( ; it!=end; ++it) {
62  delete *it;
63  *it=0;
64  }
65  effHisto_.clear();
66 }
67 
68 void LauEffModel::setEffHisto(const TH2* effHisto, Bool_t useInterpolation,
69  Bool_t fluctuateBins, Double_t avEff, Double_t absError,
70  Bool_t useUpperHalfOnly, Bool_t squareDP)
71 {
72  // Set the efficiency across the Dalitz plot using a predetermined 2D histogram
73  // with x = m_13^2, y = m_23^2.
74  Bool_t upperHalf( kFALSE );
75  if ( daughters_->gotSymmetricalDP() && useUpperHalfOnly == kTRUE) {upperHalf = kTRUE;}
76  std::cout<<"INFO in LauEffModel::setEffHisto : Efficiency histogram has upperHalf = "<<static_cast<Int_t>(upperHalf)<<std::endl;
77 
78  std::vector<Lau2DAbsDP*>::iterator it = effHisto_.begin();
79  std::vector<Lau2DAbsDP*>::iterator end = effHisto_.end();
80  for( ; it!=end; ++it) {
81  delete *it;
82  *it=0;
83  }
84  effHisto_.clear();
85 
86  // Copy the histogram.
87  effHisto_.push_back(new Lau2DHistDP(effHisto, daughters_,
88  useInterpolation, fluctuateBins,
89  avEff, absError, upperHalf, squareDP));
90  fluctuateEffHisto_ = fluctuateBins;
91 
92  if (avEff > 0.0 && absError > 0.0) {
93  fluctuateEffHisto_ = kTRUE;
94  }
95 }
96 
97 void LauEffModel::setEffHisto(const TH2* effHisto, const TH2* errorHi, const TH2* errorLo, Bool_t useInterpolation,
98  Bool_t fluctuateBins, Double_t avEff, Double_t absError,
99  Bool_t useUpperHalfOnly, Bool_t squareDP)
100 {
101  // Set the efficiency across the Dalitz plot using a predetermined 2D histogram
102  // with x = m_13^2, y = m_23^2.
103  Bool_t upperHalf( kFALSE );
104  if ( daughters_->gotSymmetricalDP() && useUpperHalfOnly == kTRUE) {upperHalf = kTRUE;}
105  std::cout<<"INFO in LauEffModel::setEffHisto : Efficiency histogram has upperHalf = "<<static_cast<Int_t>(upperHalf)<<std::endl;
106 
107  std::vector<Lau2DAbsDP*>::iterator it = effHisto_.begin();
108  std::vector<Lau2DAbsDP*>::iterator end = effHisto_.end();
109  for( ; it!=end; ++it) {
110  delete *it;
111  *it=0;
112  }
113  effHisto_.clear();
114 
115  // Copy the histogram.
116  effHisto_.push_back(new Lau2DHistDP(effHisto, errorHi, errorLo, daughters_,
117  useInterpolation, fluctuateBins,
118  avEff, absError, upperHalf, squareDP));
119  fluctuateEffHisto_ = fluctuateBins;
120 
121  if (avEff > 0.0 && absError > 0.0) {
122  fluctuateEffHisto_ = kTRUE;
123  }
124 }
125 
126 void LauEffModel::setEffSpline(const TH2* effHisto,
127  Bool_t fluctuateBins, Double_t avEff, Double_t absError,
128  Bool_t useUpperHalfOnly, Bool_t squareDP)
129 {
130  // Set the efficiency across the Dalitz plot using a predetermined 2D histogram
131  // with x = m_13^2, y = m_23^2.
132  Bool_t upperHalf( kFALSE );
133  if ( daughters_->gotSymmetricalDP() && useUpperHalfOnly == kTRUE) {upperHalf = kTRUE;}
134  std::cout<<"INFO in LauEffModel::setEffSpline : Efficiency histogram has upperHalf = "<<static_cast<Int_t>(upperHalf)<<std::endl;
135 
136  std::vector<Lau2DAbsDP*>::iterator it = effHisto_.begin();
137  std::vector<Lau2DAbsDP*>::iterator end = effHisto_.end();
138  for( ; it!=end; ++it) {
139  delete *it;
140  *it=0;
141  }
142  effHisto_.clear();
143 
144  // Copy the histogram.
145  effHisto_.push_back(new Lau2DSplineDP(effHisto, daughters_,
146  fluctuateBins, avEff, absError, upperHalf, squareDP));
147  fluctuateEffHisto_ = fluctuateBins;
148 
149  if (avEff > 0.0 && absError > 0.0) {
150  fluctuateEffHisto_ = kTRUE;
151  }
152 }
153 
154 void LauEffModel::setEffSpline(const TH2* effHisto, const TH2* errorHi, const TH2* errorLo,
155  Bool_t fluctuateBins, Double_t avEff, Double_t absError,
156  Bool_t useUpperHalfOnly, Bool_t squareDP)
157 {
158  // Set the efficiency across the Dalitz plot using a predetermined 2D histogram
159  // with x = m_13^2, y = m_23^2.
160  Bool_t upperHalf( kFALSE );
161  if ( daughters_->gotSymmetricalDP() && useUpperHalfOnly == kTRUE) {upperHalf = kTRUE;}
162  std::cout<<"INFO in LauEffModel::setEffSpline : Efficiency histogram has upperHalf = "<<static_cast<Int_t>(upperHalf)<<std::endl;
163 
164  std::vector<Lau2DAbsDP*>::iterator it = effHisto_.begin();
165  std::vector<Lau2DAbsDP*>::iterator end = effHisto_.end();
166  for( ; it!=end; ++it) {
167  delete *it;
168  *it=0;
169  }
170  effHisto_.clear();
171 
172  // Copy the histogram.
173  effHisto_.push_back(new Lau2DSplineDP(effHisto, errorHi, errorLo, daughters_,
174  fluctuateBins, avEff, absError, upperHalf, squareDP));
175  fluctuateEffHisto_ = fluctuateBins;
176 
177  if (avEff > 0.0 && absError > 0.0) {
178  fluctuateEffHisto_ = kTRUE;
179  }
180 }
181 
182 void LauEffModel::addEffHisto(const TH2* effHisto, Bool_t useInterpolation,
183  Double_t avEff, Double_t absError,
184  Bool_t useUpperHalfOnly, Bool_t squareDP)
185 {
186  // Set the efficiency across the Dalitz plot using a predetermined 2D histogram
187  // with x = m_13^2, y = m_23^2.
188  Bool_t upperHalf( kFALSE );
189  if ( daughters_->gotSymmetricalDP() && useUpperHalfOnly == kTRUE) {upperHalf = kTRUE;}
190  std::cout<<"INFO in LauEffModel::addEffHisto : Efficiency histogram has upperHalf = "<<static_cast<Int_t>(upperHalf)<<std::endl;
191 
192  // Copy the histogram.
193  effHisto_.push_back(new Lau2DHistDP(effHisto, daughters_,
194  useInterpolation, fluctuateEffHisto_,
195  avEff, absError, upperHalf, squareDP));
196 }
197 
198 void LauEffModel::addEffHisto(const TH2* effHisto, const TH2* errorHi, const TH2* errorLo, Bool_t useInterpolation,
199  Double_t avEff, Double_t absError,
200  Bool_t useUpperHalfOnly, Bool_t squareDP)
201 {
202  // Set the efficiency across the Dalitz plot using a predetermined 2D histogram
203  // with x = m_13^2, y = m_23^2.
204  Bool_t upperHalf( kFALSE );
205  if ( daughters_->gotSymmetricalDP() && useUpperHalfOnly == kTRUE) {upperHalf = kTRUE;}
206  std::cout<<"INFO in LauEffModel::addEffHisto : Efficiency histogram has upperHalf = "<<static_cast<Int_t>(upperHalf)<<std::endl;
207 
208  // Copy the histogram.
209  effHisto_.push_back(new Lau2DHistDP(effHisto, errorHi, errorLo, daughters_,
210  useInterpolation, fluctuateEffHisto_,
211  avEff, absError, upperHalf, squareDP));
212 }
213 
214 void LauEffModel::addEffSpline(const TH2* effHisto,
215  Double_t avEff, Double_t absError,
216  Bool_t useUpperHalfOnly, Bool_t squareDP)
217 {
218  // Set the efficiency across the Dalitz plot using a predetermined 2D histogram
219  // with x = m_13^2, y = m_23^2.
220  Bool_t upperHalf( kFALSE );
221  if ( daughters_->gotSymmetricalDP() && useUpperHalfOnly == kTRUE) {upperHalf = kTRUE;}
222  std::cout<<"INFO in LauEffModel::addEffSpline : Efficiency histogram has upperHalf = "<<static_cast<Int_t>(upperHalf)<<std::endl;
223 
224  // Copy the histogram.
225  effHisto_.push_back(new Lau2DSplineDP(effHisto, daughters_,
226  fluctuateEffHisto_, avEff, absError, upperHalf, squareDP));
227 }
228 
229 void LauEffModel::addEffSpline(const TH2* effHisto, const TH2* errorHi, const TH2* errorLo,
230  Double_t avEff, Double_t absError,
231  Bool_t useUpperHalfOnly, Bool_t squareDP)
232 {
233  // Set the efficiency across the Dalitz plot using a predetermined 2D histogram
234  // with x = m_13^2, y = m_23^2.
235  Bool_t upperHalf( kFALSE );
236  if ( daughters_->gotSymmetricalDP() && useUpperHalfOnly == kTRUE) {upperHalf = kTRUE;}
237  std::cout<<"INFO in LauEffModel::addEffSpline : Efficiency histogram has upperHalf = "<<static_cast<Int_t>(upperHalf)<<std::endl;
238 
239  // Copy the histogram.
240  effHisto_.push_back(new Lau2DSplineDP(effHisto, errorHi, errorLo, daughters_,
241  fluctuateEffHisto_, avEff, absError, upperHalf, squareDP));
242 }
243 
244 Double_t LauEffModel::getEffHistValue(const LauKinematics* kinematics) const
245 {
246  // Get the efficiency from the 2D histo.
247  Double_t eff(1.0);
248 
249  Double_t xVal(0.0);
250  Double_t yVal(0.0);
251 
252  std::vector<Lau2DAbsDP*>::const_iterator it = effHisto_.begin();
253  const std::vector<Lau2DAbsDP*>::const_iterator end = effHisto_.end();
254  for( ; it!=end; ++it) {
255  if ( (*it)->usingSquareDP() ) {
256  xVal = kinematics->getmPrime();
257  yVal = kinematics->getThetaPrime();
258  } else {
259  xVal = kinematics->getm13Sq();
260  yVal = kinematics->getm23Sq();
261  }
262  eff *= (*it)->interpolateXY(xVal, yVal);
263  }
264 
265  return eff;
266 }
267 
268 Double_t LauEffModel::calcEfficiency( const LauKinematics* kinematics ) const
269 {
270  // Routine to calculate the efficiency for the given event/point in
271  // the Dalitz plot. This routine uses the 2D histogram set by the
272  // setEffHisto() function.
273  Double_t eff(1.0);
274 
275  // Check for vetoes
276  Bool_t vetoOK(kTRUE);
277  if ( vetoes_ != 0 ) {
278  vetoOK = vetoes_->passVeto(kinematics);
279  }
280 
281  if (vetoOK == kFALSE) {
282  // We failed the veto.
283  eff = 0.0;
284  } else {
285  // We are using a 2D histogram representation of the efficiency across the Dalitz plot.
286  eff = this->getEffHistValue( kinematics );
287  }
288 
289  // Check that the efficiency is in the allowed range (0-1)
290  // If we're using a spline then out-of-range efficiencies can be caused by adjacent bins that all contain a value of either zero or one.
291  // The spline requires the efficiency, its first derivatives and the mixed second derivative to be continuous and to match the input histogram
292  // at the bin centres. Derivatives are calculated using a finite difference approximation taking the difference between the neighbouring bins.
293  // If two bins are zero but the third is not then the second bin will have a positive first derivative causing the spline to dip below zero
294  // between the two zero bins to remain smooth. The analogous case with adjacent maximised bins will cause peaks above one. Such dips are
295  // unavoidable but are correctly removed here.
296  if ( eff < 0.0 ) {
297  if(!lowBinWarningIssued_) {
298  std::cerr << "WARNING in LauEffModel::calcEfficiency : Efficiency " << eff << " is less than 0 - setting to 0. You may want to check your histogram!" << std::endl
299  << " : If you are using a spline then this could be caused by adjacent empty bins. Further warnings will be suppressed." << std::endl;
300  lowBinWarningIssued_=kTRUE;
301  }
302  eff = 0.0;
303  } else if ( eff > 1.0 ) {
304  if(!highBinWarningIssued_) {
305  std::cerr << "WARNING in LauEffModel::calcEfficiency : Efficiency " << eff << " is greater than 1 - setting to 1. You may want to check your histogram!" << std::endl
306  << " : If you are using a spline then this could be caused by adjacent full bins. Further warnings will be suppressed." << std::endl;
307  highBinWarningIssued_=kTRUE;
308  }
309  eff = 1.0;
310  }
311 
312  return eff;
313 }
314 
315 Bool_t LauEffModel::passVeto( const LauKinematics* kinematics ) const
316 {
317  Bool_t pass = kTRUE;
318  if ( vetoes_ != 0 ) {
319  pass = vetoes_->passVeto( kinematics );
320  }
321  return pass;
322 }
323 
File containing declaration of Lau2DSplineDP class.
Bool_t passVeto(const LauKinematics *kinematics) const
Check whether the specified Dalitz plot point passes the vetoes.
Definition: LauVetoes.cc:118
void setEffHisto(const TH2 *effHisto, Bool_t useInterpolation=kTRUE, Bool_t fluctuateBins=kFALSE, Double_t avEff=-1.0, Double_t absError=-1.0, Bool_t useUpperHalfOnly=kFALSE, Bool_t squareDP=kFALSE)
Set the efficiency variation across the phase space using a predetermined 2D histogram.
Definition: LauEffModel.cc:68
ClassImp(LauAbsCoeffSet)
const LauDaughters * daughters_
The daughters object.
Definition: LauEffModel.hh:249
Double_t getmPrime() const
Get m&#39; value.
Class that defines the particular 3-body decay under study.
Definition: LauDaughters.hh:47
void addEffHisto(const TH2 *effHisto, Bool_t useInterpolation=kTRUE, Double_t avEff=-1.0, Double_t absError=-1.0, Bool_t useUpperHalfOnly=kFALSE, Bool_t squareDP=kFALSE)
Add a multiplicative efficiency variation across the phase space using a predetermined 2D histogram...
Definition: LauEffModel.cc:182
File containing declaration of LauDaughters class.
Double_t getm23Sq() const
Get the m23 invariant mass square.
Double_t getEffHistValue(const LauKinematics *kinematics) const
Get the efficiency from a two-dimensional histogram.
Definition: LauEffModel.cc:244
File containing declaration of LauKinematics class.
Bool_t gotSymmetricalDP() const
Is Dalitz plot symmetric, i.e. 2 identical particles.
Definition: LauDaughters.hh:80
Bool_t passVeto(const LauKinematics *kinematics) const
Determine whether the given DP position is outside the vetoes.
Definition: LauEffModel.cc:315
Double_t calcEfficiency(const LauKinematics *kinematics) const
Determine the efficiency for a given point in the Dalitz plot.
Definition: LauEffModel.cc:268
Bool_t highBinWarningIssued_
Flag to track whether a warning has been issued for bin values greater than one.
Definition: LauEffModel.hh:264
void setEffSpline(const TH2 *effHisto, Bool_t fluctuateBins=kFALSE, Double_t avEff=-1.0, Double_t absError=-1.0, Bool_t useUpperHalfOnly=kFALSE, Bool_t squareDP=kFALSE)
Set the efficiency variation across the phase space using a spline based on a predetermined 2D histog...
Definition: LauEffModel.cc:126
const LauVetoes * vetoes_
The vetoes object.
Definition: LauEffModel.hh:252
File containing declaration of Lau2DHistDP class.
Bool_t lowBinWarningIssued_
Flag to track whether a warning has been issued for bin values less than zero.
Definition: LauEffModel.hh:261
File containing declaration of LauEffModel class.
Class that implements the efficiency description across the signal Dalitz plot.
Definition: LauEffModel.hh:51
Double_t getm13Sq() const
Get the m13 invariant mass square.
Class for defining a 2D DP histogram.
Definition: Lau2DHistDP.hh:48
Double_t getThetaPrime() const
Get theta&#39; value.
Class for calculating 3-body kinematic quantities.
std::vector< Lau2DAbsDP * > effHisto_
The efficiency histogram objects.
Definition: LauEffModel.hh:255
File containing declaration of LauVetoes class.
Bool_t fluctuateEffHisto_
Fluctuate histogram within the error.
Definition: LauEffModel.hh:258
void addEffSpline(const TH2 *effHisto, Double_t avEff=-1.0, Double_t absError=-1.0, Bool_t useUpperHalfOnly=kFALSE, Bool_t squareDP=kFALSE)
Add a multiplicative efficiency variation across the phase space using a spline based on a predetermi...
Definition: LauEffModel.cc:214
Class for defining vetoes within the Dalitz plot.
Definition: LauVetoes.hh:50
virtual ~LauEffModel()
Destructor.
Definition: LauEffModel.cc:57
Class for defining variations across a 2D DP using a spline.