CMS 3D CMS Logo

 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Macros Groups Pages
MuonResidualsBfieldAngleFitter.cc
Go to the documentation of this file.
2 
4 
6 
7 void MuonResidualsBfieldAngleFitter_FCN(int &npar, double *gin, double &fval, double *par, int iflag) {
10  MuonResidualsFitter *fitter = fitinfo->fitter();
11 
12  fval = 0.;
13  for (std::vector<double *>::const_iterator resiter = fitter->residuals_begin(); resiter != fitter->residuals_end();
14  ++resiter) {
15  const double residual = (*resiter)[MuonResidualsBfieldAngleFitter::kResidual];
16  const double qoverpt = (*resiter)[MuonResidualsBfieldAngleFitter::kQoverPt];
17  const double qoverpz = (*resiter)[MuonResidualsBfieldAngleFitter::kQoverPz];
18 
19  double center = 0.;
21  center += par[MuonResidualsBfieldAngleFitter::kBfrompt] * qoverpt;
22  center += par[MuonResidualsBfieldAngleFitter::kBfrompz] * qoverpz;
23  center += par[MuonResidualsBfieldAngleFitter::kdEdx] * (1. / qoverpt / qoverpt + 1. / qoverpz / qoverpz) *
24  (qoverpt > 0. ? 1. : -1.);
25 
28  } else if (fitter->residualsModel() == MuonResidualsFitter::kPowerLawTails) {
31  } else if (fitter->residualsModel() == MuonResidualsFitter::kROOTVoigt) {
34  } else if (fitter->residualsModel() == MuonResidualsFitter::kGaussPowerTails) {
36  } else {
37  assert(false);
38  }
39  }
40 }
41 
43  initialize_table(); // if not already initialized
44 
45  double sum_x = 0.;
46  double sum_xx = 0.;
47  int N = 0;
48 
49  for (std::vector<double *>::const_iterator resiter = residuals_begin(); resiter != residuals_end(); ++resiter) {
50  const double residual = (*resiter)[kResidual];
51  // const double qoverpt = (*resiter)[kQoverPt];
52 
53  if (fabs(residual) < 0.1) { // truncate at 100 mrad
54  sum_x += residual;
55  sum_xx += residual * residual;
56  N++;
57  }
58  }
59 
60  if (N < m_minHits)
61  return false;
62 
63  // truncated mean and stdev to seed the fit
64  double mean = sum_x / double(N);
65  double stdev = sqrt(sum_xx / double(N) - pow(sum_x / double(N), 2));
66 
67  // refine the standard deviation calculation
68  sum_x = 0.;
69  sum_xx = 0.;
70  N = 0;
71  for (std::vector<double *>::const_iterator resiter = residuals_begin(); resiter != residuals_end(); ++resiter) {
72  const double residual = (*resiter)[kResidual];
73  if (mean - 1.5 * stdev < residual && residual < mean + 1.5 * stdev) {
74  sum_x += residual;
75  sum_xx += residual * residual;
76  N++;
77  }
78  }
79  mean = sum_x / double(N);
80  stdev = sqrt(sum_xx / double(N) - pow(sum_x / double(N), 2));
81 
82  sum_x = 0.;
83  sum_xx = 0.;
84  N = 0;
85  for (std::vector<double *>::const_iterator resiter = residuals_begin(); resiter != residuals_end(); ++resiter) {
86  const double residual = (*resiter)[kResidual];
87  if (mean - 1.5 * stdev < residual && residual < mean + 1.5 * stdev) {
88  sum_x += residual;
89  sum_xx += residual * residual;
90  N++;
91  }
92  }
93  mean = sum_x / double(N);
94  stdev = sqrt(sum_xx / double(N) - pow(sum_x / double(N), 2));
95 
96  std::vector<int> parNum;
97  std::vector<std::string> parName;
98  std::vector<double> start;
99  std::vector<double> step;
100  std::vector<double> low;
101  std::vector<double> high;
102 
103  parNum.push_back(kAngle);
104  parName.push_back(std::string("angle"));
105  start.push_back(mean);
106  step.push_back(0.1);
107  low.push_back(0.);
108  high.push_back(0.);
109  parNum.push_back(kBfrompt);
110  parName.push_back(std::string("bfrompt"));
111  start.push_back(0.);
112  step.push_back(0.1 * stdev / 0.05);
113  low.push_back(0.);
114  high.push_back(0.);
115  parNum.push_back(kBfrompz);
116  parName.push_back(std::string("bfrompz"));
117  start.push_back(0.);
118  step.push_back(0.1 * stdev / 0.05);
119  low.push_back(0.);
120  high.push_back(0.);
121  parNum.push_back(kdEdx);
122  parName.push_back(std::string("dEdx"));
123  start.push_back(0.);
124  step.push_back(0.1 * stdev / 0.05);
125  low.push_back(0.);
126  high.push_back(0.);
127  parNum.push_back(kSigma);
128  parName.push_back(std::string("sigma"));
129  start.push_back(stdev);
130  step.push_back(0.1 * stdev);
131  low.push_back(0.);
132  high.push_back(0.);
134  parNum.push_back(kGamma);
135  parName.push_back(std::string("gamma"));
136  start.push_back(stdev);
137  step.push_back(0.1 * stdev);
138  low.push_back(0.);
139  high.push_back(0.);
140  }
141 
142  return dofit(&MuonResidualsBfieldAngleFitter_FCN, parNum, parName, start, step, low, high);
143 }
144 
146  std::stringstream raw_name, narrowed_name, qoverpt_name, qoverpz_name, psquared_name;
147  raw_name << name << "_raw";
148  narrowed_name << name << "_narrowed";
149  qoverpt_name << name << "_qoverpt";
150  qoverpz_name << name << "_qoverpz";
151  psquared_name << name << "_psquared";
152 
153  TH1F *raw_hist =
154  dir->make<TH1F>(raw_name.str().c_str(), (raw_name.str() + std::string(" (mrad)")).c_str(), 100, -100., 100.);
155  TH1F *narrowed_hist = dir->make<TH1F>(
156  narrowed_name.str().c_str(), (narrowed_name.str() + std::string(" (mrad)")).c_str(), 100, -100., 100.);
157  TProfile *qoverpt_hist = dir->make<TProfile>(
158  qoverpt_name.str().c_str(), (qoverpt_name.str() + std::string(" (mrad)")).c_str(), 100, -0.05, 0.05);
159  TProfile *qoverpz_hist = dir->make<TProfile>(
160  qoverpz_name.str().c_str(), (qoverpz_name.str() + std::string(" (mrad)")).c_str(), 100, -0.05, 0.05);
161  TProfile *psquared_hist = dir->make<TProfile>(
162  psquared_name.str().c_str(), (psquared_name.str() + std::string(" (mrad)")).c_str(), 100, -0.05, 0.05);
163 
164  narrowed_name << "fit";
165  qoverpt_name << "fit";
166  qoverpz_name << "fit";
167  psquared_name << "fit";
168 
169  double scale_factor = double(numResiduals()) * (100. - -100.) / 100; // (max - min)/nbins
170 
171  TF1 *narrowed_fit = nullptr;
172  if (residualsModel() == kPureGaussian) {
173  narrowed_fit = new TF1(narrowed_name.str().c_str(), MuonResidualsFitter_pureGaussian_TF1, -100., 100., 3);
174  narrowed_fit->SetParameters(scale_factor, value(kAngle) * 1000., value(kSigma) * 1000.);
175  narrowed_fit->Write();
176  } else if (residualsModel() == kPowerLawTails) {
177  narrowed_fit = new TF1(narrowed_name.str().c_str(), MuonResidualsFitter_powerLawTails_TF1, -100., 100., 4);
178  narrowed_fit->SetParameters(scale_factor, value(kAngle) * 1000., value(kSigma) * 1000., value(kGamma) * 1000.);
179  narrowed_fit->Write();
180  } else if (residualsModel() == kROOTVoigt) {
181  narrowed_fit = new TF1(narrowed_name.str().c_str(), MuonResidualsFitter_ROOTVoigt_TF1, -100., 100., 4);
182  narrowed_fit->SetParameters(scale_factor, value(kAngle) * 1000., value(kSigma) * 1000., value(kGamma) * 1000.);
183  narrowed_fit->Write();
184  } else if (residualsModel() == kGaussPowerTails) {
185  narrowed_fit = new TF1(narrowed_name.str().c_str(), MuonResidualsFitter_GaussPowerTails_TF1, -100., 100., 3);
186  narrowed_fit->SetParameters(scale_factor, value(kAngle) * 1000., value(kSigma) * 1000.);
187  narrowed_fit->Write();
188  }
189 
190  TF1 *qoverpt_fit = new TF1(qoverpt_name.str().c_str(), "[0]+x*[1]", -0.05, 0.05);
191  qoverpt_fit->SetParameters(value(kAngle) * 1000., value(kBfrompt) * 1000.);
192  qoverpt_fit->Write();
193 
194  TF1 *qoverpz_fit = new TF1(qoverpz_name.str().c_str(), "[0]+x*[1]", -0.05, 0.05);
195  qoverpz_fit->SetParameters(value(kAngle) * 1000., value(kBfrompz) * 1000.);
196  qoverpz_fit->Write();
197 
198  TF1 *psquared_fit = new TF1(psquared_name.str().c_str(), "[0]+[1]*x**2", -0.05, 0.05);
199  psquared_fit->SetParameters(value(kAngle) * 1000., value(kdEdx) * 1000.);
200  psquared_fit->Write();
201 
202  for (std::vector<double *>::const_iterator resiter = residuals_begin(); resiter != residuals_end(); ++resiter) {
203  const double raw_residual = (*resiter)[kResidual];
204  const double qoverpt = (*resiter)[kQoverPt];
205  const double qoverpz = (*resiter)[kQoverPz];
206  const double psquared = (1. / qoverpt / qoverpt + 1. / qoverpz / qoverpz) * (qoverpt > 0. ? 1. : -1.);
207 
208  double qoverpt_correction = value(kBfrompt) * qoverpt;
209  double qoverpz_correction = value(kBfrompz) * qoverpz;
210  double dEdx_correction = value(kdEdx) * psquared;
211  double corrected_residual = raw_residual - qoverpt_correction - qoverpz_correction - dEdx_correction;
212 
213  raw_hist->Fill(raw_residual * 1000.);
214  narrowed_hist->Fill(corrected_residual * 1000.);
215 
216  qoverpt_hist->Fill(qoverpt, (raw_residual - qoverpz_correction - dEdx_correction) * 1000.);
217  qoverpz_hist->Fill(qoverpz, (raw_residual - qoverpt_correction - dEdx_correction) * 1000.);
218  psquared_hist->Fill(psquared, (raw_residual - qoverpt_correction - qoverpz_correction) * 1000.);
219  }
220 
221  return 0.;
222 }
double MuonResidualsFitter_logGaussPowerTails(double residual, double center, double sigma)
std::vector< double * >::const_iterator residuals_begin() const
Double_t MuonResidualsFitter_powerLawTails_TF1(Double_t *xvec, Double_t *par)
MuonResidualsFitter * fitter()
double value(int parNum)
assert(be >=bs)
bool dofit(void(*fcn)(int &, double *, double &, double *, int), std::vector< int > &parNum, std::vector< std::string > &parName, std::vector< double > &start, std::vector< double > &step, std::vector< double > &low, std::vector< double > &high)
double MuonResidualsFitter_logROOTVoigt(double residual, double center, double sigma, double gamma)
void inform(TMinuit *tMinuit) override
double plot(std::string name, TFileDirectory *dir, Alignable *ali) override
T sqrt(T t)
Definition: SSEVec.h:19
double MuonResidualsFitter_logPowerLawTails(double residual, double center, double sigma, double gamma)
Double_t MuonResidualsFitter_GaussPowerTails_TF1(Double_t *xvec, Double_t *par)
T * make(const Args &...args) const
make new ROOT object
Double_t MuonResidualsFitter_pureGaussian_TF1(Double_t *xvec, Double_t *par)
#define N
Definition: blowfish.cc:9
static TMinuit * MuonResidualsBfieldAngleFitter_TMinuit
std::vector< double * >::const_iterator residuals_end() const
step
Definition: StallMonitor.cc:98
Double_t MuonResidualsFitter_ROOTVoigt_TF1(Double_t *xvec, Double_t *par)
void MuonResidualsBfieldAngleFitter_FCN(int &npar, double *gin, double &fval, double *par, int iflag)
double MuonResidualsFitter_logPureGaussian(double residual, double center, double sigma)
Power< A, B >::type pow(const A &a, const B &b)
Definition: Power.h:29