65 #if !defined(__CINT__) || defined(__MAKECINT__)
67 #include "Riostream.h"
78 #include "TFitResult.h"
89 #include "StLaserAnalysisMaker/LaserEvent.h"
90 #include "TDataSetIter.h"
92 #include "TTreeIter.h"
95 static Int_t date = 0;
96 static Int_t Time = 0;
98 static Double_t DVAll[2][3];
99 static Double_t dDVAll[2][3];
100 static Int_t _debug = 0;
101 static Double_t sigmaAcceptedDV = 5e-4;
108 TH2D *dMembraneY[2][2][2];
111 Float_t run, date, time, events, day, dvAll, ddvAll, dvWest, ddvWest, dvEast, ddvEast, slAll, dslAll, slWest, dslWest, slEast, dslEast;
112 Float_t vWest, vEast, zWI, dzWI, zEI, dzEI, zWO, dzWO, zEO, dzEO, utime, ok, dvSet, XWI, dXWI, XEI, dXEI, XWO, dXWO, XEO, dXEO, YWI, dYWI, YEI, dYEI, YWO, dYWO, YEO, dYEO;
114 const Char_t *vRun =
"run:date:time:events:day:dvAll:ddvAll:dvWest:ddvWest:dvEast:ddvEast:slAll:dslAll:slWest:dslWest:slEast:dslEast:vWest:vEast:zWI:dzWI:zEI:dzEI:zWO:dzWO:zEO:dzEO:utime:ok:dvSet:XWI:dXWI:XEI:dXEI:XWO:dXWO:XEO:dXEO:YWI:dYWI:YEI:dYEI:YWO:dYWO:YEO:dYEO";
117 Double_t memDelay(Double_t *x, Double_t *p) {
118 static Double_t MembraneDelay[2][24] = {
121 {398.122,367.481,342.294,332.015,341.383,366.056,396.65,424.512,443.64 ,450.607,444.276,425.678,448.44 ,455.407,449.076,430.478,402.922,372.281,347.094,336.815,346.183,370.856,401.45,429.312},
122 {424.573,373.866,329.379,310.108,327.703,371.43 ,422.198,466.33,495.816,506.426,496.787,468.144,500.616,511.226,501.587,472.944,429.373,378.666,334.179,314.908,332.503,376.23,426.998,471.13}};
123 Int_t sector = TMath::Nint(x[0]);
125 if (sector < 1 || sector > 24)
return value;
126 Int_t inout = TMath::Nint(p[0]);
127 if (inout < 0 || inout > 1)
return value;
128 return p[1] + p[2]*MembraneDelay[inout][sector-1];
131 TF1 *MemDelay(Int_t inout = 0) {
132 TF1 *f =
new TF1(
"MemDelay",memDelay,-0.5,24.5,3);
133 f->SetParameters(inout,0,1);
134 f->SetParNames(
"InOut",
"Shift",
"Scale");
135 f->FixParameter(0,inout);
139 Double_t ScaleE2W(Double_t day) {
141 static Double_t par[2] = {1.57361e-01,-4.59752e-03};
142 return par[0] + par[1]*day;
146 Double_t dv = DVAll[0][0];
147 Double_t ddv = dDVAll[0][0];
148 Double_t dvWest = DVAll[0][1];
149 Double_t ddvWest = dDVAll[0][1];
150 Double_t dvEast = DVAll[0][2];
151 Double_t ddvEast = dDVAll[0][2];
153 if (dvWest < 5.3 || dvWest > 5.9 || ddvWest <= 0 || ddvWest>sigmaAcceptedDV ||
154 dvEast < 5.3 || dvEast > 5.9 || ddvEast <= 0 || ddvEast>sigmaAcceptedDV) {
157 cout <<
"Run " << run <<
" fails ============================= to make separated East and West drift velocities" << endl;
158 cout <<
"vWest = " << dvWest <<
" +/- " << ddvWest
159 <<
"\tvEast = " << dvEast <<
" +/- " << ddvEast << endl;
162 #ifndef SeparateWestandEast
166 if (Run.ok == 1 && (dv < 5.3 || dv > 5.9 || ddv <= 0 || ddv >sigmaAcceptedDV)) {
167 cout <<
"Run " << run <<
" fails ============================= to make averaged drift velocities" << endl;
168 cout <<
"v = " << dv <<
" +/- " << ddv << endl;
171 if (Run.ok == 2 && (Run.date < 130101 || Run.date > 140000 && Run.date < 150000))
return;
173 if (Run.dzWO > 2e-3 || Run.dzEO > 2e-3 ||
174 Run.zWO + Run.zEO < 409.9 ||
175 Run.zWO + Run.zEO > 410.5) {Run.ok = 3;
return;}
186 dv = 1e-6*Run.vWest*(1. + (5.85670e-01 -1.42815e-03*(Run.zWO + Run.zEO)));
188 TString fOut = Form(
"tpcDriftVelocity.%8i.%06i.C",date,Time);
190 cout <<
"Create " << fOut << endl;
191 out.open(fOut.Data());
192 out <<
"TDataSet *CreateTable() {" << endl;
193 out <<
" if (!gROOT->GetClass(\"St_tpcDriftVelocity\")) return 0;" << endl;
194 out <<
" St_tpcDriftVelocity *tableSet = new St_tpcDriftVelocity(\"tpcDriftVelocity\",1);" << endl;
195 out <<
" tpcDriftVelocity_st row;// Laser Run " << run << endl;
196 out <<
" memset(&row, 0, tableSet->GetRowSize());"<< endl;
199 out <<
" row.laserDriftVelocityEast = " << dvEast <<
"; // +/- " << ddvEast
200 <<
" cm/us East: Slope = " << DVAll[1][2] <<
" +/- " << dDVAll[1][2] <<
" DV = " << dvEast <<
" +/- " << ddvEast
202 out <<
" row.laserDriftVelocityWest = " << dvWest <<
"; // +/- " << ddvWest
203 <<
" cm/us West: Slope = " << DVAll[1][1] <<
" +/- " << dDVAll[1][1] <<
" DV = " << dvWest <<
" +/- " << ddvWest<< endl;
204 out <<
" tableSet->AddAt(&row); " << endl;
205 out <<
" return (TDataSet *)tableSet; // 1e3*Delta: All = " << dv <<
" +/- " << ddv << endl;
208 out <<
" row.laserDriftVelocityEast = " << dv <<
"; // +/- " << ddv
209 <<
" cm/us All: East = " << DVAll[1][2] <<
" +/- " << dDVAll[1][2];
210 if (Run.ok == 2) out <<
" From Membrane";
212 out <<
" row.laserDriftVelocityWest = " << dv <<
"; // +/- " << ddv
213 <<
" cm/us All: West = " << DVAll[1][1] <<
" +/- " << dDVAll[1][1] << endl;
214 out <<
" tableSet->AddAt(&row);// 1e3*Delta: All = " << dv <<
" +/- " << ddv << endl;
215 out <<
" return (TDataSet *)tableSet;//"
216 <<
" West = " << dvWest <<
" +/- " << ddvWest
217 <<
" East = " << dvEast <<
" +/- " << ddvEast << endl;
223 static TDatime t0(2007,1,1,0,0,0);
224 static UInt_t u0 = t0.Convert();
225 date = 20000000 + (Int_t) Run.date;
226 Time = (Int_t) Run.time;
227 TDatime t(date, Time);
228 Run.utime = t.Convert();
229 Run.day = 1. + (Run.utime - u0)/(24.*60.*60.);
230 run = (Int_t) (1000000*((Int_t) (Run.date/1000000)) + Run.run);
231 memset(&DVAll[0][0], 0, 6*
sizeof(Double_t));
232 memset(&dDVAll[0][0], 0, 6*
sizeof(Double_t));
234 Run.events = slope->GetEntries();
235 cout <<
"Run " << run <<
" has " << Run.events <<
" entries" << endl;
236 TH2D *hist[2] = {dv, slope};
237 Float_t *par = &Run.dvAll;
238 for (Int_t l = 0; l < 2; l++) {
239 #ifdef ADJUSTABLE_BINNING
240 hist[l]->BufferEmpty();
243 hist[l]->FitSlicesY(0,1,0,10,
"QNRI");
244 TString fitN(hist[l]->GetName());
246 TH1D *fit = (TH1D *) gDirectory->Get(fitN);
249 TAxis *xax = fit->GetXaxis();
250 Int_t sector16 = xax->FindBin(16.);
251 fit->SetBinError(sector16, 1.0);
252 Int_t sector8 = xax->FindBin(8.);
253 fit->SetBinError(sector8, 1.0);
255 fit->SetMarkerStyle(20);
256 Double_t xmin = fit->GetXaxis()->GetXmin();
257 Double_t xmax = fit->GetXaxis()->GetXmax();
258 TF1 *pol0 = (TF1*) gROOT->GetFunction(
"pol0");
260 for (Int_t k = 0; k < 3; k++) {
261 pol0->SetLineColor(k+1);
274 Int_t status = fit->Fit(pol0,opt,
"",x1,x2);
276 DVAll[l][k] = pol0->GetParameter(0);
277 dDVAll[l][k] = pol0->GetParError(0);
279 par[2*(k+3*l)] = DVAll[l][k];
280 par[2*(k+3*l)+1] = dDVAll[l][k];
286 for (Int_t io = 0; io < 2; io++) {
287 zMembrane[io]->FitSlicesY(0,1,0,10,
"QNRI");
288 TString fitN(zMembrane[io]->GetName());
290 TH1D *fit = (TH1D *) gDirectory->Get(fitN);
292 fit->SetMarkerStyle(20);
293 Float_t *par = &Run.zWI;
294 for (Int_t we = 0; we < 2; we++) {
295 TF1 *pol0 = (TF1*) gROOT->GetFunction(
"pol0");
296 if (we == 0) fit->Fit(pol0,
"er",
"",0.5,12.5);
297 else fit->Fit(pol0,
"er+",
"",12.5,24.5);
298 par[4*io+2*we ] = pol0->GetParameter(0);
299 par[4*io+2*we+1] = pol0->GetParError(0);
304 for (Int_t xy = 0; xy < 2; xy++) {
305 for (Int_t io = 0; io < 2; io++) {
306 Float_t *par = &Run.XWI;
307 for (Int_t we = 0; we < 2; we++) {
308 dMembraneY[io][we][xy]->FitSlicesY(0,1,0,10,
"QNRI");
309 TString fitN(dMembraneY[io][we][xy]->GetName());
311 TH1D *fit = (TH1D *) gDirectory->Get(fitN);
313 fit->SetMarkerStyle(20);
314 TF1 *pol1 = (TF1*) gROOT->GetFunction(
"pol1");
315 Int_t status = fit->Fit(pol1);
317 par[8*xy+4*io+2*we ] = pol1->GetParameter(1)/210;
318 par[8*xy+4*io+2*we+1] = pol1->GetParError(1)/210;
320 par[8*xy+4*io+2*we ] = -999;
321 par[8*xy+4*io+2*we+1] = 999;
328 runNT->Fill(&Run.run);
331 void LanaTrees(
const Char_t *files=
"./st_laser_*.laser.root",
const Char_t *Out =
"LaserPlots.root") {
333 const Char_t *TreeName =
"laser";
334 TChain *tree =
new TChain(TreeName);
336 while ((file = (Char_t *) Dir.NextFile())) {
340 tree->SetBranchAddress(
"event", &event);
342 TFile *fOut =
new TFile(Out,
"recreate");
343 runNT =
new TNtuple(
"RunNT",
"Run date time",vRun);
344 static const Double_t EastWRTWestDiff = 0;
346 Double_t OnlFreq = 0;
348 Double_t oldDate = -1;
349 TDatime t0(2007,1,1,0,0,0);
350 UInt_t ut0 = t0.Convert();
351 Long64_t nentries = tree->GetEntriesFast();
352 Long64_t nbytes = 0, nb = 0;
353 for (Long64_t jentry=0; jentry<nentries;jentry++) {
354 Long64_t ientry = tree->LoadTree(jentry);
355 if (ientry < 0)
break;
356 nb = tree->GetEntry(jentry); nbytes += nb;
359 for (Int_t i = 0; i < NZFR; i++) {
if (ZFieldRuns[i] == event->GetHeader()->fRun) {iok = i;
break;}}
360 if (iok >= 0)
continue;
362 if (event->GetHeader()->fRun != oldRun) {
363 OnlFreq =
event->GetHeader()->fOnlClock;
365 TDatime t(event->GetHeader()->fDate,
event->GetHeader()->fTime);
366 UInt_t ut = t.Convert();
367 Double_t Date = 1. + (ut - ut0)/(24.*60.*60.);
368 #ifdef INTEGRATE_OVER_HOURS
369 if (Date - oldDate > 0.125) {
371 if (oldRun != -1) Fit();
372 cout <<
"New run " <<
event->GetHeader()->fRun <<
" Date Old/New " << oldDate <<
"/" << Date << endl;
373 Run.run =
event->GetHeader()->fRun%1000000;
374 Run.date =
event->GetHeader()->fDate%1000000;
375 Run.time =
event->GetHeader()->fTime;
376 Run.vWest =
event->GetHeader()->fDriVelWest;
377 Run.vEast =
event->GetHeader()->fDriVelEast;
379 #ifdef ADJUSTABLE_BINNING
380 dv =
new TH2D(Form(
"DV%i",event->GetHeader()->fRun%1000000),Form(
"Drift Velocity for run %i",event->GetHeader()->fRun%1000000),12,1,25,400,1,-1);
381 dv->SetBuffer(100000);
383 dv =
new TH2D(Form(
"DV%i",event->GetHeader()->fRun%1000000),Form(
"Drift Velocity for run %i",event->GetHeader()->fRun%1000000),12,1,25,2000,5.3,5.9);
385 dv->SetXTitle(
"Sector");
386 dv->SetYTitle(
"Drift Velocity ");
387 #ifdef ADJUSTABLE_BINNING
388 slope =
new TH2D(Form(
"SL%i",event->GetHeader()->fRun%1000000),Form(
"Slope for run %i",event->GetHeader()->fRun%1000000),12,1,25,400,1,-1);
389 slope->SetBuffer(100000);
391 slope =
new TH2D(Form(
"SL%i",event->GetHeader()->fRun%1000000),Form(
"Slope for run %i",event->GetHeader()->fRun%1000000),12,1,25,2000,-10.,10.);
393 slope->SetXTitle(
"Sector");
394 slope->SetYTitle(
"Difference wrt reference Drift Velocity in pemill");
395 memAdc =
new TH2D(Form(
"memAdc%i", event->GetHeader()->fRun%1000000),
396 Form(
"Log(Adc) @ Membrane for West and East, Inner and Outer sectors for run %i",event->GetHeader()->fRun%1000000),
397 4, 0.5, 4.5, 100, 0, 10);
398 for (Int_t io = 0; io < 2; io++) {
400 TString title(
"Z[cm] of Membrane");
401 if (io == 0) {name +=
"I"; title +=
" Inner";}
402 else {name +=
"O"; title +=
" Outer";}
403 name += Form(
"%i",event->GetHeader()->GetRun()%1000000);
404 title += Form(
" for run %i",event->GetHeader()->GetRun()%1000000);
406 zMembrane[io] =
new TH2D(name,title,24,0.5,24.5,200,200,210);
407 for (Int_t we = 0; we < 2; we++) {
408 for (Int_t xy = 0; xy < 2; xy++) {
409 name =
"R"; name += Form(
"%i",event->GetHeader()->GetRun()%1000000);
410 title =
"Drift length for Membrane clusters versus";
411 if (xy == 0) {name +=
"X"; title +=
" X. ";}
412 else {name +=
"Y"; title +=
" Y. ";}
413 if (io == 0) {name +=
"I"; title +=
" Inner";}
414 else {name +=
"O"; title +=
" Outer";}
415 if (we == 0) {name +=
"W"; title +=
" West";}
416 else {name +=
"E"; title +=
" East";}
417 dMembraneY[io][we][xy] =
new TH2D(name,title,100,-200,200,1000,-10,10);
421 oldRun = (Int_t) event->GetHeader()->GetRun();
423 #ifdef INTEGRATE_OVER_HOURS
428 for (Int_t i = 0; i <
event->GetNhit(); i++) {
429 Hit *
hit = (
Hit *) event->Hits()->UncheckedAt(i);
430 Int_t io = 0;
if (hit->row > 13) io = 1;
431 zMembrane[io]->Fill(hit->sector,hit->xyzL.z());
432 Int_t we = 0;
if (hit->sector > 12) we = 1;
433 dMembraneY[io][we][0]->Fill(hit->xyz.x(),hit->xyzTpcL.z());
434 dMembraneY[io][we][1]->Fill(hit->xyz.y(),hit->xyzTpcL.z());
435 if (TMath::Abs(TMath::Abs(hit->xyzTpcL.z())-205) < 25 && hit->adc > 0) memAdc->Fill(2.*we + io + 1., TMath::Log(hit->adc));
438 Double_t dt =
event->GetHeader()->fDate%1000000 + ((Double_t) event->GetHeader()->fTime)*1e-6;
439 Double_t DT = Run.date + Run.time*1e-6;
441 Run.date =
event->GetHeader()->fDate%1000000;
442 Run.time =
event->GetHeader()->fTime;
444 for (Int_t k = 0; k < 12; k++) {
445 FitDV *fit = (
FitDV *) event->Fit()->UncheckedAt(k);
448 if (fit->ndf > 2 && fit->Prob > 1.e-2) {
449 Double_t Slope = 1e3*fit->slope;
450 if (fit->Sector > 12) Slope -= EastWRTWestDiff;
451 slope->Fill(fit->Sector, Slope);
452 Double_t Vm = OnlFreq/
event->GetHeader()->fClock;
453 if (fit->Sector <= 12) Vm *=
event->GetHeader()->fDriVelWest;
454 else Vm *=
event->GetHeader()->fDriVelEast;
455 Double_t V = 1e-6*Vm/(1.+1e-3*Slope-Vm/TMath::Ccgs());
456 dv->Fill(fit->Sector,V);
462 memset (Flag, 0, 42*
sizeof(Double_t));
464 for (Int_t i = 0; i < N; i++) {
468 for (Int_t i = 0; i < N; i++) {
if (TMath::Abs(fit->Y[i] - YA) > 10) Flag[i] = 1;}
472 for (Int_t i = 0; i < N; i++) {
473 if (! fit->Flag[i]) {
474 Double_t dev = fit->Y[i]/sigma;
476 Double_t a[2] = {1./sigma, fit->X[i]/sigma};
480 Int_t ndf = A.GetNrows() - 2;
482 TRSymMatrix S(A,TRArray::kATxA);
if (_debug) cout <<
"S: " << S << endl;
483 TRVector B(A,TRArray::kATxB,Y);
if (_debug) cout <<
"B: " << B << endl;
484 TRSymMatrix SInv(S,TRArray::kInverted);
if (_debug) cout <<
"SInv: " << SInv << endl;
485 TRVector X(SInv,TRArray::kSxA,B);
if (_debug) cout <<
"X: " << X << endl;
487 R -=
TRVector(A,TRArray::kAxB,X);
if (_debug) cout <<
"R: " << R << endl;
488 Double_t chisq = R*R;
489 Double_t prob = TMath::Prob(chisq,ndf);
491 Double_t offset = X[0];
492 Double_t slope = X[1];
493 Double_t chisq = chisq;
494 Double_t dslope = SInv[2];
495 Double_t doffset = SInv[0];
496 if (ndf > 4 && prob > 1.e-2) {
497 Double_t Slope = 1e3*slope;
498 if (fit->Sector > 12) Slope -= EastWRTWestDiff;
499 slope->Fill(fit->Sector, Slope);
500 Double_t Vm = OnlFreq/
event->GetHeader()->fClock*
event->GetHeader()->fDriVel;
501 Double_t V = 1e-6*Vm/(1.+1e-3*Slope-Vm/TMath::Ccgs());
502 dv->Fill(fit->Sector,V);
510 for (Int_t i = 0; i < N; i++) {
511 if (! fit->Flag[i]) {
513 Double_t RR = TMath::Abs(R[j]);
545 Double_t OffSets(Double_t *x) {
548 static Double_t Toffsets[12] = {10.33, 3.34, 6.14, 13.11, -1., 17.31,
549 19.88, 12.95, 5.97, 3.18, 10.17, 17.14};
550 static Double_t DV = 55.42840e-4;
551 Int_t sector2 = (Int_t) ((x[0]-1)/2.);
553 if (sector2 < 0 || sector2 > 12)
return off;
554 return DV*Toffsets[sector2];