StRoot  1
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Groups Pages
makeVernierScanFitFromHist.C
1 int use_background=1;
2 int x_end=4;
3 
4 #define runB
5 
6 #ifdef runA
7 #define jan 1
8 // for run 10097097
9 float x[]={.00, .10, .20, .35, .50, .75, 1.0,
10  .00,-.10,-.20,-.35,-.50,-.75,-1.0,.00,
11  0,0,0,0,0,0,0,
12  0,0,0,0,0,0,0,0};//milimeters
13 float y[]={0,0,0,0,0,0,0,
14  0,0,0,0,0,0,0,0,
15  .00, .10, .20, .35, .50, .75, 1.0,
16  .00,-.10,-.20,-.35,-.50,-.75,-1.0,.00};//milimeters
17 int timediff[]={00,35,35,37,36,37,37,41,35,35,37,35,37,37,42,
18  31,35,36,36,35,37,38,41,35,35,35,36,37,37,42};//s
19 float Nblue=11349.49/107;//10^9 Ions
20 float Nyellow=10274.33/107;//10^9 Ions
21 int Nbunches=98;//96;
22 int max_time=1220;
23 float kbb=1036758;//from vernier/wcm using xml right before run.
24 //
25 #endif
26 
27 #ifdef runB
28 #define jan 2
29 //for run 10103044
30 float x[]={.00, .15, .30, .45, .60, .75, .90,
31  .00,-.15,-.30,-.45,-.60,-.75,-.90,.00,
32  0,0,0,0,0,0,0,
33  0,0,0,0,0,0,0,0};//milimeters
34 float y[]={0,0,0,0,0,0,0,
35  0,0,0,0,0,0,0,0,
36  .00, .15, .30, .45, .60, .75, .90,
37  .00,-.15,-.30,-.45,-.60,-.75,-.90,.00};//milimeters
38 int timediff[]={00,36,37,36,36,36,36,41,36,36,36,36,36,36,41,
39  31,36,35,36,36,36,36,41,37,36,36,36,36,36,41};//s
40 float Nblue=10505.05/106;//10^9 Ions
41 float Nyellow=10039.98/106;//10^9 Ions
42 int Nbunches=96;
43 int max_time=1400;
44 float kbb=938419;//from vernier/wcm using xml right before run.
45 //
46 #endif // end of setup switch between runs
47 
48 int integration_width=30;
49 float *x_longname ,*y_longname ;
50 bool extra_use;
51 
52 float frequency=9.383/120.0; //MHz*buckets / buckets
53 
54 Double_t gaus_stepping(Double_t *v, Double_t *par)
55 {
56  Double_t skfNN=par[0]/1e7*frequency*kbb;
57  //sigma*10^24 / s
58  //since we subsume the 10^24, sigma*10^24/mm^2==unitless
59  //hence, sigma is in units of 10^-24mm^2=10^-26cm^2=.01 barns
60  //if we input sigma in nanobarns (my preference for the fit),
61  //then we must divide by 10^7 to get the number of centibarns:
62  //printf("skfNN=%f\n",skfNN);
63  Double_t sx2=par[1];//sigx1*sigx1+sigx2*sigx2; //milimeters^2
64  Double_t sy2=par[2];//sigy1*sigy1+sigy2*sigy2; //milimeters^2
65  Double_t background=par[3];
66 
67 
68  Int_t step=v[0];
69  if (step>29)
70  {
71  printf("Requested step out of bounds, for drawing. This shouldn't be possible.\n");
72  return -999;
73  }
74  Double_t dx=x [step];
75  Double_t dy=y [step];
76 
77  if (dx*dx>1.1 || dy*dy>1.1)
78  {
79  printf("v[0]=%f,step=%d ==> dx=%f, dy=%f\n",v[0],step,dx,dy);
80  printf("Array out of bounds. Checking arrays:\n");
81  for(int i=0;i<30;i++)
82  printf("step=%d x=%1.2f y=%1.2f\n",i,x [i],y [i]);
83  assert(1==2);
84  }
85 
86  if (dx*dx>(x[x_end]*x[x_end]*.95) || dy*dy>(x[x_end]*x[x_end]*.95))
87  return use_background*background*integration_width;
88 
89  if ((sx2*sy2)<0.00000001)
90  {
91  printf("gaus_Step with: 0=%f,1=%f,2=%f\n",skfNN,sx2,sy2);
92  return 999;
93  }
94 
95  //comment me back in!
96  Double_t sL= skfNN/(2*TMath::Pi()*sqrt(sx2*sy2));
97  //Double_t sL= 18.84+9.44;
98  Double_t val=sL*exp(-dx*dx/(2*sx2))*exp(-dy*dy/(2*sy2));
99 
100  /*we now have the expected /rate/, but since we integrated over a certain number of seconds, we
101  need to multiple to get the expected counts. N=rate*time
102  */
103  //printf("gaus_Step: 0=%f,1=%f,2=%f,3=%f,4=%f ===> %f\n",skfNN,sigx1,sigx2,sigy1,sigy2, val*20.0);
104  //don't forget to add in the background rate!
105  return (val+background)*integration_width;
106 }
107 
108 
109 //==============================
110 void janNicePlot(TH1F * hin){
111  printf("AAA\n");
112  char txt[1000];
113 
114  int runID=999999;
115  float yMax=999;
116  if(jan==1) {
117  runID=10097097;
118  yMax=1290;
119  }
120  if(jan==2) {
121  runID=10103044;
122  yMax=850;
123  }
124 
125  sprintf(txt,"BHT3 yield for R%d; vernier scan i-th step",runID);
126  hin->SetTitle(txt);
127  hin->SetMaximum(yMax);
128  hin->SetMarkerStyle(8);
129  hin->SetMarkerColor(kBlue);
130 
131  sprintf(txt,"vernierR%dbht3_1gaus",runID);
132  c2=new TCanvas(txt,txt,450,600);
133  c2->cd();
134 
135  TPad *cU,*cD; splitPadY(0.4,&cU,&cD);
136  cU->cd();
137  hin->SetStats(0);//temp
138  hin->Draw("e");
139  gStyle->SetOptStat(0);
140  gStyle->SetOptFit(11111);
141 
142  TF1 *ff=hin->GetFunction("steppy"); assert(ff);
143  float nb=hin->GetNbinsX();
144 
145  TH1F *hdif=(TH1F*) hin->Clone();
146  hdif->Reset();
147  sprintf(txt,"yield residua; step index; data-fit");
148  hdif->SetTitle(txt);
149 
150  float par0=ff->GetParameter(0);
151  float erPar0=ff->GetParError(0);
152  float relEr=erPar0/par0;
153  printf("par0=%f +/- %f , relEr=%f\n",par0,erPar0,relEr);
154 
155  for(int k=1;k<=nb;k++) {
156  float x=hin->GetBinCenter(k);
157  float y=hin->GetBinContent(k);
158  float ey=hin->GetBinError(k);
159  float fy=ff->Eval(x);
160  float eFit=relEr*fy;
161  float totEr=sqrt(ey*ey+eFit*eFit);
162  // printf("k=%d %f %f %f %f\n",k,x,y,ey,fy);
163  hdif->SetBinContent(k,y-fy);
164  hdif->SetBinError(k,totEr);
165  }
166  cD->cd();
167  hdif->Draw("e");
168  hdif->SetMaximum(yMax/10.);
169  hdif->SetMinimum(-yMax/10.);
170  ln=new TLine(0,0,30,0); ln->SetLineStyle(2);ln->Draw();ln->SetLineColor(kBlack);
171 
172 }
173 
174 //------------------------
175 void splitPadY(float y, TPad **cU, TPad **cD) {
176  (*cU) = new TPad("padD", "apdD",0,y+0.005,1.0,1.);
177  (*cU)->Draw();
178  (*cD) = new TPad("padU", "apdU",0.0,0.,1.,y);
179  (*cD)->Draw();
180 
181  /* use case:
182  TPad *cU,*cD; splitPadY(0.4,&cU,&cD);
183  cU->cd(); h->Draw()
184  */
185 }
186 
187 
188 //==============================
189 void makeVernierScanFitFromHist(char * infile="temp.hist.root")
190 {
191  if(jan==1) infile="10097097.bht3.hist.root";
192  if(jan==2) infile="10103044.bht3.hist.root";
193 
194  TFile *f=new TFile(infile);
195  TH1F* times=(TH1F*)(f->Get("time"));
196 
197  float *xpos=x;
198  float *ypos=y;
199  int counts[30];
200  int timestamp[30];
201 
202  timestamp[0]=timediff[0];
203  for (int i=1;i<30;i++)
204  timestamp[i]=timediff[i]+timestamp[i-1];
205  //according to Angelika Drees, these timestamps represent the time that the file was saved, and hence is ~1 second /after/ the end of data-taking for that step. At timestamp[0], the beam should be moving from x=0 to x=0.10.
206 
207 
208  TH1F *stamps=new TH1F("timestamps","timestamps",max_time,0,max_time);
209 
210 
211  //timestamps of the big jumps: 6,13,21,28
212 
213  //find the offfset between the time stamps and the data by maximizing the differential across each jump:
214 
215  int best_value=0;
216  int best_offset=-1;
217 
218  int temp_value=0;
219  TH1F *hOffset=new TH1F("offset","summed differential across big steps as a function of proposed offset;offset;dHz/dt",600,0,600);
220  for (int i=4;i+timestamp[28]<max_time;i++)
221  {
222  temp_value=0;
223  temp_value-=times->GetBinContent(i+timestamp[6]-2);
224  temp_value-=times->GetBinContent(i+timestamp[6]-1);
225  temp_value+=times->GetBinContent(i+timestamp[6]+1);
226  temp_value+=times->GetBinContent(i+timestamp[6]+2);
227 
228  temp_value-=times->GetBinContent(i+timestamp[13]-2);
229  temp_value-=times->GetBinContent(i+timestamp[13]-1);
230  temp_value+=times->GetBinContent(i+timestamp[13]+1);
231  temp_value+=times->GetBinContent(i+timestamp[13]+2);
232 
233  temp_value-=times->GetBinContent(i+timestamp[21]-2);
234  temp_value-=times->GetBinContent(i+timestamp[21]-1);
235  temp_value+=times->GetBinContent(i+timestamp[21]+1);
236  temp_value+=times->GetBinContent(i+timestamp[21]+2);
237 
238  temp_value-=times->GetBinContent(i+timestamp[28]-2);
239  temp_value-=times->GetBinContent(i+timestamp[28]-1);
240  temp_value+=times->GetBinContent(i+timestamp[28]+1);
241  temp_value+=times->GetBinContent(i+timestamp[28]+2);
242  hOffset->Fill(i,temp_value);
243  if (temp_value>best_value)
244  {
245  best_value=temp_value;
246  best_offset=i;
247  }
248  }
249  hOffset->Draw();
250  printf("Best offset is %d\n",best_offset);
251 
252 
253  //Have: Correct offset
254  //define the ranges we intend to integrate over for each step:
255  int end_offset=5;//give us a buffer of five seconds between the end of our range and the timestamp that apparently occurs ~1 second after the step ended.
256  int start_offset=25;//give us a substantial buffer from the end of the previous to make sure we're well clear of the beam motion.
257 
258  //change that to be a generalized width (defined above):
259  end_offset=16-integration_width/2;
260  start_offset=end_offset+integration_width;
261 
262  for (int i=0;i<30;i++)
263  {
264  counts[i]=0;
265  // printf("summing bin %d to %d for new bin %d\n",
266  // best_offset+timestamp[i]-start_offset,
267  // best_offset+timestamp[i]-end_offset,
268  // i);
269  for (int j=best_offset+timestamp[i]-start_offset;
270  j<(best_offset+timestamp[i]-end_offset);j++)
271  counts[i]+=times->GetBinContent(j);
272  }
273 
274  TH1F *idealized=new TH1F("idealized","counts vs step;step;counts",30,0,30);
275  //gStyle->SetOptStat(1);
276  //gStyle->SetOptFit(11101);
277  //printf("Step\tXPos\tYPos\tCounts\n");
278  for (int i=0;i<30;i++)
279  //printf("%d\t%f\t%f\t%d\n",i,x[i],y[i],counts[i]-1.7*integration_width);
280  //return;
281  idealized->Fill(i,counts[i]);
282  idealized->GetYaxis()->SetRangeUser(0,1600);
283  //idealized->Draw("e");
284 
285  //N=L*sigma
286  //N=kfNN*1/(2pi sqrt(sigx1^2+sigx2^2)sqrt(sigx1^2+sigy2^2)) * exp(-d^2/2(sigx1^2+sigx2^2))
287  //NN=11349.49*10274.33*10^18
288 
289  //define errors:
290  float err_counts[30];
291  for (int i=0;i<30;i++)
292  err_counts[i]=sqrt(counts[i]);
293 
294  float err_pos[30];
295  for (int i=0;i<30;i++)
296  err_pos[i]=0.01;
297 
298  x_longname=xpos;
299  y_longname=ypos;
300 
301  /*testing the function:
302  Double_t a[1];
303  Double_t b[]={1.0,1.0,1.0,1.1,1.1};
304  for (int i=0;i<30;i++)
305  {
306  printf("step: i=%d ==>I=%f\n ",i,i*1.0);
307  a[0]=i*1.0;
308  gaus_stepping(a,b);
309  }
310  return;
311  */
312 
313  TF1 *func=new TF1("steppy",gaus_stepping,0.1,29.9,4);
314  func->SetParameters(2,0.25,0.25,.05);
315  //old: func->SetParNames("skfNN","sigx_blue","sigx_yellow","sigy_blue","sigy_yellow");
316  func->SetParNames("sigma (nb)","#sigma_{X}^{2} (mm^{2})","#sigma_{Y}^{2^} (mm^{2})","background (Hz)");
317  //func->SetParLimits(0,1000*1000,5000*1000);
318  func->SetParLimits(1,0.01,10);
319  func->SetParLimits(2,0.01,10);
320  //func->SetParLimits(3,0,0.1);
321 
322 
323  idealized->Fit("steppy");
324  // func->Draw();
325  //func->SetParameter(0,342);
326  //func->SetParameter(1,0.0180);
327  //func->SetParameter(2,0.0125);
328  //func->SetParameter(3,1.72);
329 
330  idealized->Draw("e");
331  //func->Draw("same");
332 
333  janNicePlot(idealized);
334 
335  return;
336 
337  Double_t a[1];
338  Double_t b[]={4.997,.1733,-0.068,.1323,.1323};
339  TF1 *copyfunc=new TF1("copy",gaus_stepping,0.1,29.9,4);
340  copyfunc->SetParameters(b);
341  copyfunc->Draw("SAME");
342 
343  for (int w=0;w<30;w+=1)
344  {
345  a[0]=w;
346  printf("bin=%f counts=%f, func=%f\n",w,gaus_stepping(a,b),func->Eval(w*1.0));
347  }
348 
349  return;
350 }