CrossCorrelator.cxx
1 #include "CrossCorrelator.h"
2 
3 #include "AnitaDataset.h"
4 #include "FilterStrategy.h"
5 
6 Acclaim::CrossCorrelator::CrossCorrelator(){
7  initializeVariables();
8 }
9 
10 
11 Acclaim::CrossCorrelator::~CrossCorrelator(){
12 }
13 
14 
15 
16 void Acclaim::CrossCorrelator::initializeVariables(){
17 
18  kDeltaPhiSect = 2;
19  multiplyTopRingByMinusOne = 0;
20 
21 
22  // Initialize with NULL otherwise very bad things will happen with gcc
23  for(Int_t pol = AnitaPol::kHorizontal; pol < AnitaPol::kNotAPol; pol++){
24  for(Int_t ant=0; ant<NUM_SEAVEYS; ant++){
25  interpRMS[pol][ant] = 0;
26  interpRMS2[pol][ant] = 0;
27  }
28  }
29 
30  kOnlyThisCombo = -1;
31  numSamples = PAD_FACTOR*NUM_SAMP; // Factor of two for padding. Turns circular xcor into linear xcor.
32  numSamplesUpsampled = numSamples*UPSAMPLE_FACTOR; // For upsampling
33 
34  nominalSamplingDeltaT = NOMINAL_SAMPLING_DELTAT;
35  correlationDeltaT = nominalSamplingDeltaT/UPSAMPLE_FACTOR;
36 
37  do5PhiSectorCombinatorics();
38 }
39 
40 
41 
42 
43 void Acclaim::CrossCorrelator::do5PhiSectorCombinatorics(){
44  // For checking later...
45  for(Int_t ant1=0; ant1 < NUM_SEAVEYS; ant1++){
46  for(Int_t ant2=0; ant2 < NUM_SEAVEYS; ant2++){
47  comboIndices[ant1][ant2] = -1;
48  }
49  }
50 
51  numCombos=0;
52  for(Int_t ant1=0; ant1<NUM_SEAVEYS; ant1++){
53  Double_t phiSect1 = ant1%NUM_PHI;
54  for(Int_t ant2=ant1+1; ant2<NUM_SEAVEYS; ant2++){
55  Double_t phiSect2 = ant2%NUM_PHI;
56 
57  if(TMath::Abs(phiSect1 - phiSect2) <= DELTA_PHI_SECT || TMath::Abs(phiSect1 - phiSect2) >= (NUM_PHI-DELTA_PHI_SECT)){
58  comboIndices[ant1][ant2] = numCombos;
59  comboIndices[ant2][ant1] = numCombos;
60  comboToAnt1s.push_back(ant1);
61  comboToAnt2s.push_back(ant2);
62  numCombos++;
63  }
64  }
65  }
66  if(numCombos != NUM_COMBOS){
67  std::cerr << "Warning! in = " << __PRETTY_FUNCTION__ << std::endl;
68  std::cerr << "\tnumCombos = " << numCombos << "." << std::endl;
69  std::cerr << "\tNUM_COMBOS = " << NUM_COMBOS << "." << std::endl;
70  std::cerr << "\tExpecting NUM_COMBOS == numCombos." << std::endl;
71  std::cerr << "\tSeriously bad things are probably about to happen." << std::endl;
72  std::cerr << "\tCheck the combinatorics!" << std::endl;
73  }
74 
75  fillCombosToUse();
76 }
77 
78 
79 
80 
81 
82 
83 Double_t Acclaim::CrossCorrelator::getCrossCorrelation(AnitaPol::AnitaPol_t pol, Int_t combo, Double_t deltaT) const{
84 
85  Int_t ant1 = comboToAnt1s[combo];
86  Int_t ant2 = comboToAnt2s[combo];
87  // std::cerr << ant1 << "\t" << ant2 << "\t" << deltaT << "\t";
88 
89  deltaT += startTimes[pol][ant1];
90  deltaT -= startTimes[pol][ant2];
91  // deltaT += startTimes[pol][ant2];
92  // deltaT -= startTimes[pol][ant1];
93 
94  // std::cerr << deltaT << std::endl;
95  Int_t offsetLow = floor(deltaT/nominalSamplingDeltaT);
96  Double_t dt1 = offsetLow*nominalSamplingDeltaT;
97  Double_t interpPrefactor = (deltaT - dt1)/nominalSamplingDeltaT;
98  offsetLow += numSamples/2; // account for time ordering correlations in internal memory (i.e. dt=0 is half way thrugh the array)
99 
100  Double_t c1 = crossCorrelations[pol][combo][offsetLow];
101  Double_t c2 = crossCorrelations[pol][combo][offsetLow+1];
102  Double_t cInterp = interpPrefactor*(c2 - c1) + c1;
103 
104  return cInterp;
105  // return c1;
106 
107 }
108 
109 
110 
111 void Acclaim::CrossCorrelator::getNormalizedInterpolatedTGraphs(const FilteredAnitaEvent* fEv,
112  AnitaPol::AnitaPol_t pol, bool raw){
113 
114  for(Int_t ant=0; ant < NUM_SEAVEYS; ant++){
115  const AnalysisWaveform* wf = raw ? fEv->getRawGraph(ant, pol) : fEv->getFilteredGraph(ant, pol);
116  const TGraphAligned* gr = wf->even();
117  startTimes[pol][ant] = gr->GetX()[0];
118  int n = gr->GetN();
119 
120  Double_t invertFactor = multiplyTopRingByMinusOne > 0 && ant < NUM_PHI ? -1 : 1;
121 
122  Double_t sumOfV = 0;
123  for(int samp=0; samp < n; samp++){
124  Double_t V = invertFactor*gr->GetY()[samp];
125  fVolts[pol][ant][samp] = V;
126  sumOfV += V;
127  }
128 
129  Double_t meanV = sumOfV/n;
130 
131  Double_t sumOfVSquared = 0;
132  for(int samp=0; samp < n; samp++){
133  fVolts[pol][ant][samp] -= meanV;
134  sumOfVSquared += fVolts[pol][ant][samp]*fVolts[pol][ant][samp];
135  }
136 
137  for(int samp=n; samp < numSamples; samp++){
138  fVolts[pol][ant][samp] = 0;
139  }
140 
141  interpRMS[pol][ant] = TMath::Sqrt(sumOfVSquared/numSamples);
142  interpRMS2[pol][ant] = TMath::Sqrt(sumOfVSquared/numSamplesUpsampled);
143  }
144 }
145 
146 
147 
148 
149 void Acclaim::CrossCorrelator::doFFTs(AnitaPol::AnitaPol_t pol){
150 
151  for(Int_t ant=0; ant<NUM_SEAVEYS; ant++){
152  FancyFFTs::doFFT(numSamples, fVolts[pol][ant], ffts[pol][ant]);
153  renormalizeFourierDomain(pol, ant);
154  }
155 }
156 
157 
158 
159 void Acclaim::CrossCorrelator::renormalizeFourierDomain(AnitaPol::AnitaPol_t pol, Int_t ant){
160  FancyFFTs::normalizeFourierDomain(numSamples, ffts[pol][ant]);
161 }
162 
163 
164 
165 
166 void Acclaim::CrossCorrelator::correlateEvent(const FilteredAnitaEvent* fEv){
167 
168  for(Int_t pol = AnitaPol::kHorizontal; pol < AnitaPol::kNotAPol; pol++){
169  correlateEvent(fEv, (AnitaPol::AnitaPol_t)pol);
170  }
171 }
172 
173 
174 void Acclaim::CrossCorrelator::correlateEvent(const FilteredAnitaEvent* fEv, AnitaPol::AnitaPol_t pol){
175 
176  // Read TGraphs from events into memory (also deletes old TGraphs)
177  // getFftsAndStartTimes(fEv, pol);
178  eventNumber[pol] = fEv->getHeader()->eventNumber;
179 
180  getNormalizedInterpolatedTGraphs(fEv, pol);
181  doFFTs(pol);
182 
183  // std::cout << "here" << std::endl;
184  doCrossCorrelations(pol);
185 
186 }
187 
188 void Acclaim::CrossCorrelator::doCrossCorrelations(AnitaPol::AnitaPol_t pol){
189 
190  // Set variable for use in threads
191 
192  Double_t* ccInternalArray = FancyFFTs::getRealArray(std::pair<int, int>(numSamples, 0));
193 
194  for(int combo=0; combo<NUM_COMBOS; combo++){
195  Int_t ant1 = comboToAnt1s.at(combo);
196  Int_t ant2 = comboToAnt2s.at(combo);
197  FancyFFTs::crossCorrelatePadded(numSamples,
198  1,
199  ffts[pol][ant2],
200  ffts[pol][ant1],
201  crossCorrelations[pol][combo],
202  false,
203  0,
204  false);
205  const int offset = numSamples/2;
206 
207  // copies first half of original array (times >= 0) into second half of internal storage
208  for(Int_t samp=0; samp < numSamples/2; samp++){
209  crossCorrelations[pol][combo][samp+offset] = ccInternalArray[samp];
210  // ptr->crossCorrelations[pol][combo][samp+offset] = stash[samp];
211  }
212  // copies second half of original array (times < 0) into first half of internal storage
213  for(Int_t samp=numSamples/2; samp < numSamples; samp++){
214  crossCorrelations[pol][combo][samp-offset] = ccInternalArray[samp];
215  // ptr->crossCorrelations[pol][combo][samp-offset] = stash[samp];
216  }
217  }
218 
219 }
220 
221 
222 void Acclaim::CrossCorrelator::doUpsampledCrossCorrelations(AnitaPol::AnitaPol_t pol, Int_t phiSector){
223 
224 
225  const std::vector<Int_t>* combosToUse = &combosToUseGlobal[phiSector];
226  Int_t numCombosToUpsample = combosToUse->size();
227 
228  Double_t* ccInternalArray = FancyFFTs::getRealArray(std::pair<int, int>(numSamplesUpsampled, 0));
229 
230  for(int comboInd=0; comboInd<numCombosToUpsample; comboInd++){
231  Int_t combo = combosToUse->at(comboInd);
232 
233  Int_t ant1 = comboToAnt1s.at(combo);
234  Int_t ant2 = comboToAnt2s.at(combo);
235 
236  FancyFFTs::crossCorrelatePadded(numSamples,
237  UPSAMPLE_FACTOR,
238  ffts[pol][ant2],
239  ffts[pol][ant1],
240  crossCorrelationsUpsampled[pol][combo],
241  false,
242  0, false);
243 
244  const int offset = numSamplesUpsampled/2;
245 
246  // copies first half of original array (times >= 0) into second half of internal storage
247  for(Int_t samp=0; samp < numSamplesUpsampled/2; samp++){
248  crossCorrelationsUpsampled[pol][combo][samp+offset] = ccInternalArray[samp];
249  }
250  // copies second half of original array (times < 0) into first half of internal storage
251  for(Int_t samp=numSamplesUpsampled/2; samp < numSamplesUpsampled; samp++){
252  crossCorrelationsUpsampled[pol][combo][samp-offset] = ccInternalArray[samp];
253  }
254  }
255 }
256 
257 
258 
259 
260 
261 Bool_t Acclaim::CrossCorrelator::useCombo(Int_t ant1, Int_t ant2, Int_t phiSector, Int_t deltaPhiSect){
262 
263  // I want to be able to choose whether or not require one of the antennas to be the phi-sector
264  // of interest or just to have both in range of deltaPhiSect.
265  // I'm going to use the sign of deltaPhiSect to do this.
266  // If deltaPhiSect < 0 this implies one of the antenna pairs must be in an l3Triggered phi-sector
267 
268  Int_t absDeltaPhiSect = TMath::Abs(deltaPhiSect);
269 
270  // Require that the difference in phi-sectors be <= absDeltaPhiSect
271  Int_t phiSectorOfAnt1 = ant1%NUM_PHI;
272  Bool_t ant1InRange = TMath::Abs(phiSector - (phiSectorOfAnt1))<=absDeltaPhiSect;
273 
274  // Takes account of wrapping around payload (e.g. antennas in phi-sectors 1 and 16 are neighbours)
275  ant1InRange = ant1InRange || TMath::Abs(phiSector - (phiSectorOfAnt1))>=(NUM_PHI-absDeltaPhiSect);
276 
277  Int_t phiSectorOfAnt2 = ant2%NUM_PHI;
278  Bool_t ant2InRange = TMath::Abs(phiSector - (phiSectorOfAnt2))<=absDeltaPhiSect;
279  ant2InRange = ant2InRange || TMath::Abs(phiSector - (phiSectorOfAnt2))>=(NUM_PHI-absDeltaPhiSect);
280 
281  // See rather rant above.
282  Bool_t extraCondition = true;
283  if(deltaPhiSect < 0){
284  extraCondition = (phiSectorOfAnt1==phiSector || phiSectorOfAnt2==phiSector);
285  }
286 
287  return (ant1InRange && ant2InRange && extraCondition);
288 }
289 
290 
291 void Acclaim::CrossCorrelator::fillCombosToUse(){
292 
293  for(Int_t phiSector = 0; phiSector<NUM_PHI; phiSector++){
294  if(combosToUseGlobal[phiSector].size() == 0){
295  for(Int_t combo=0; combo<numCombos; combo++){
296  Int_t ant1 = comboToAnt1s.at(combo);
297  Int_t ant2 = comboToAnt2s.at(combo);
298  if(useCombo(ant1, ant2, phiSector, kDeltaPhiSect)){
299  combosToUseGlobal[phiSector].push_back(combo);
300  }
301  }
302  }
303  }
304 }
305 
306 
307 
308 
309 Double_t Acclaim::CrossCorrelator::getInterpolatedUpsampledCorrelationValue(AnitaPol::AnitaPol_t pol,
310  Int_t combo, Double_t deltaT) const{
311 
312  Int_t offsetLow = floor(deltaT/correlationDeltaT);
313 
314  Double_t dt1 = offsetLow*correlationDeltaT;
315  // Double_t dt2 = offsetHigh*ptr->correlationDeltaT;
316 
317  const Int_t offset = numSamplesUpsampled/2;
318  offsetLow += offset;
319  Int_t offsetHigh = offsetLow+1;
320 
321  // offsetLow = offsetLow < 0 ? offsetLow + numSamplesUpsampled : offsetLow;
322  // offsetHigh = offsetHigh < 0 ? offsetHigh + numSamplesUpsampled : offsetHigh;
323 
324  Double_t c1 = crossCorrelationsUpsampled[pol][combo][offsetLow];
325  Double_t c2 = crossCorrelationsUpsampled[pol][combo][offsetHigh];
326 
327  Double_t cInterp = (deltaT - dt1)*(c2 - c1)/(correlationDeltaT) + c1;
328 
329  return cInterp;
330 
331 }
332 
333 
334 Double_t Acclaim::CrossCorrelator::getTimeOfMaximumUpsampledCrossCorrelation(AnitaPol::AnitaPol_t pol, Int_t ant1, Int_t ant2) const{
335  Int_t combo = comboIndices[ant1][ant2];
336  if(combo < 0){
337  return -999;
338  }
339  Int_t maxSamp = TMath::LocMax(numSamplesUpsampled, crossCorrelationsUpsampled[pol][combo]);
340  maxSamp = maxSamp > numSamplesUpsampled/2 ? maxSamp - numSamplesUpsampled : maxSamp;
341  return maxSamp*correlationDeltaT;
342 }
343 
344 
345 
346 TGraph* Acclaim::CrossCorrelator::getCrossCorrelationGraphWorker(Int_t numSamps, AnitaPol::AnitaPol_t pol,
347  Int_t ant1, Int_t ant2) const {
348  // Primarily for debugging, put cross correlations in a TGraph
349 
350  Int_t combo = comboIndices[ant1][ant2];
351  if(combo < 0){
352  return NULL;
353  }
354 
355  Double_t graphDt = correlationDeltaT;
356  const Double_t* corrPtr = crossCorrelationsUpsampled[pol][combo];
357  if(numSamps != numSamplesUpsampled){
358  numSamps = numSamples;
359  graphDt = nominalSamplingDeltaT;
360  corrPtr = crossCorrelations[pol][combo];
361  }
362 
363  // Could actually perform the calculation here... but I'll leave it NULL for now
364  if(corrPtr==NULL){
365  return NULL;
366  }
367 
368  std::vector<Double_t> offsets = std::vector<Double_t>(numSamps, 0);
369  std::vector<Double_t> corrs = std::vector<Double_t>(numSamps, 0);
370 
371  // put the correlations in, in time order in memory
372 
373  for(Int_t i=0; i<numSamps; i++){
374  Int_t offset = (i - numSamps/2);
375  offsets.at(i) = offset*graphDt;
376  corrs.at(i) = corrPtr[i];
377  }
378 
379 
380  TGraph* gr = new TGraph(numSamps, &offsets[0], &corrs[0]);
381  if(numSamps != numSamplesUpsampled){
382  gr->SetName(TString::Format("grCorr_%d_%d", ant1, ant2));
383  gr->SetTitle(TString::Format("Cross Correlation ant1 = %d, ant2 = %d", ant1, ant2));
384  }
385  else{
386  gr->SetName(TString::Format("grCorrUpsampled_%d_%d", ant1, ant2));
387  gr->SetTitle(TString::Format("Upsampled Cross Correlation ant1 = %d, ant2 = %d", ant1, ant2));
388  }
389 
390  return gr;
391 }
392 
393 TGraph* Acclaim::CrossCorrelator::getCrossCorrelationGraph(AnitaPol::AnitaPol_t pol, Int_t ant1, Int_t ant2) const {
394  // Primarily for debugging, put cross correlations in a TGraph
395  return getCrossCorrelationGraphWorker(numSamples, pol, ant1, ant2);
396 }
397 
398 TGraph* Acclaim::CrossCorrelator::getUpsampledCrossCorrelationGraph(AnitaPol::AnitaPol_t pol, Int_t ant1, Int_t ant2) const {
399  return getCrossCorrelationGraphWorker(numSamplesUpsampled, pol, ant1, ant2);
400 }
401 
402 
403 
404 
405 
406 
407 
408 
409 
410 
411 
412 
413 
414 
415 
416 
417 
418 
419 
420 
427 Acclaim::TemplateCorrelator::TemplateCorrelator(Int_t run, UInt_t eventNumber){
428  // std::cerr << __PRETTY_FUNCTION__ << std::endl;
429  initializeVariables();
430  initTemplate(run, eventNumber);
431 }
432 
438  // std::cerr << __PRETTY_FUNCTION__ << std::endl;
439 }
440 
441 
442 
443 
450 void Acclaim::TemplateCorrelator::initTemplate(Int_t run, UInt_t eventNumber){
451  // std::cerr << __PRETTY_FUNCTION__ << std::endl;
452  AnitaDataset d(run);
453  d.getEvent(eventNumber);
454  FilterStrategy fs;
455  FilteredAnitaEvent fEv(d.useful(), &fs, d.gps(), d.header());
456  initTemplate(&fEv);
457 }
458 
459 
460 
467  // std::cerr << __PRETTY_FUNCTION__ << std::endl;
468 
469  // std::cerr << fEv->getHeader()->run << "\t" << fEv->getHeader()->eventNumber << std::endl;
470  for(int polInd=0; polInd < AnitaPol::kNotAPol; polInd++){
472  getNormalizedInterpolatedTGraphs(fEv, pol, true);
473  doFFTs(pol);
474 
475  // for(int ant=0; ant < NUM_SEAVEYS; ant++){
476  // std::cerr << startTimes[pol][ant] << "\t" << interpRMS[pol][ant] << "\t" << interpRMS2[pol][ant] << "\t"
477  // << (interpRMS[pol][ant]*interpRMS[pol][ant])/(interpRMS2[pol][ant]*interpRMS2[pol][ant]) << std::endl;
478  // }
479  }
480 
481 }
482 
483 
490  for(int polInd=0; polInd < AnitaPol::kNotAPol; polInd++){
492  this->correlateEvent(fEv, pol);
493  }
494 }
495 
496 
497 
498 
499 
507 
508  const int nf = GET_NUM_FREQS(numSamples);
509  std::vector<std::complex<double> > fftTemp(nf);
510  std::vector<double> vTemp(numSamples);
511  std::vector<double> ccTemp(numSamples);
512 
513 
514  for(int ant=0; ant < NUM_SEAVEYS; ant++){
515  const AnalysisWaveform* wf = fEv->getRawGraph(ant, pol);
516  const TGraphAligned* gr = wf->even();
517 
518  for(int i=0; i < gr->GetN(); i++){
519  vTemp[i] = gr->GetY()[i];
520  }
521  for(int i=gr->GetN(); i < numSamples; i++){
522  vTemp[i] = 0;
523  }
524  FancyFFTs::doFFT(numSamples, &vTemp[0], &fftTemp[0]);
525 
526  // This doesn't get used in the template case,
527  // so repurpose this variable in TemplateCorrelator
528  interpRMS2[pol][ant] = gr->GetX()[0];
529  // const FFTWComplex* chanFFT = wf->freq();
530 
531  FancyFFTs::normalizeFourierDomain(numSamples, &fftTemp[0]);
532 
533  FancyFFTs::crossCorrelatePadded(numSamples,
534  1,
535  &fftTemp[0],
536  ffts[pol][ant],
537  &ccTemp[0],
538  // crossCorrelations[pol][ant],
539  true,
540  0,
541  false);
542  const int offset = numSamples/2;
543 
544  // copies first half of original array (times >= 0) into second half of internal storage
545  for(Int_t samp=0; samp < numSamples/2; samp++){
546  crossCorrelations[pol][ant][samp+offset] = ccTemp[samp];
547  }
548  // copies second half of original array (times < 0) into first half of internal storage
549  for(Int_t samp=numSamples/2; samp < numSamples; samp++){
550  crossCorrelations[pol][ant][samp-offset] = ccTemp[samp];
551  }
552  }
553  // double meanVolts = sumVolts/n;
554  // double wholePolRMS = (sumSqVolts/n) - (meanVolts*meanVolts);
555  // double norm = 1.; ///(wholePolRMS*numSamples*numSamples);
556  double norm = 1./(numSamples*numSamples);
557 
558  for(int ant=0; ant < NUM_SEAVEYS; ant++){
559  for(Int_t samp=0; samp < numSamples; samp++){
560  crossCorrelations[pol][ant][samp]*=norm;
561  }
562  }
563 }
564 
565 
566 
567 
577 
578  double deltaT = 0;
579  deltaT += interpRMS2[pol][ant];
580  deltaT -= startTimes[pol][ant];
581 
582  double offsetTime = -0.5*numSamples*NOMINAL_SAMPLING_DELTAT;
583 
584  TGraph* gr = new TGraph(numSamples);
585  TString title = TString::Format("Template Cross-correlation - ant %d ", ant+1);
586  title += pol == AnitaPol::kHorizontal ? "HPol" : "VPol";
587  gr->SetTitle(title);
588  for(int i=0; i < numSamples; i++){
589  gr->SetPoint(i, offsetTime, crossCorrelations[pol][ant][i]);
590  offsetTime += NOMINAL_SAMPLING_DELTAT;
591  }
592 
593  return gr;
594 }
595 
596 
597 
598 
599 
600 
601 
602 Double_t Acclaim::TemplateCorrelator::getCrossCorrelation(AnitaPol::AnitaPol_t pol, Int_t ant, Double_t deltaT) const{
603 
604  deltaT += interpRMS2[pol][ant];
605  deltaT -= startTimes[pol][ant];
606 
607  Int_t offsetLow = floor(deltaT/nominalSamplingDeltaT);
608  Double_t dt1 = offsetLow*nominalSamplingDeltaT;
609  Double_t interpPrefactor = (deltaT - dt1)/nominalSamplingDeltaT;
610  offsetLow += numSamples/2; // account for time ordering correlations in internal memory (i.e. dt=0 is half way thrugh the array)
611 
612  Double_t c1 = crossCorrelations[pol][ant][offsetLow];
613  Double_t c2 = crossCorrelations[pol][ant][offsetLow+1];
614  Double_t cInterp = interpPrefactor*(c2 - c1) + c1;
615 
616  return cInterp;
617 }
618 
619 
620 
621 
622 
623 
624 Double_t Acclaim::TemplateCorrelator::getPeakCorrelation(AnitaPol::AnitaPol_t pol, Double_t minOffset, Double_t maxOffset, Double_t stepSize) const{
625 
626  double dt = minOffset;
627  double bestDt = 0;
628  double bestCorr = -DBL_MAX;
629  while(dt < maxOffset){
630 
631  double thisCorr = 0;
632  for(int ant=0; ant < NUM_SEAVEYS; ant++){
633  thisCorr += this->getCrossCorrelation(pol, ant, dt);
634  }
635 
636  if(thisCorr > bestCorr){
637  bestCorr = thisCorr;
638  bestDt = dt;
639  }
640 
641  dt += stepSize;
642  }
643 
644  // std::cerr << pol << "\t" << bestDt << "\t" << bestCorr << std::endl;
645  return bestCorr;
646 }
virtual void correlateEvent(const FilteredAnitaEvent *fEv)
TemplateCorrelator(Int_t run, UInt_t eventNumber)
int getEvent(int eventNumber, bool quiet=false)
A filter strategy defines the sets of filters that are used and provides some introspection abilities...
USeful in for loops.
TGraph * getCrossCorrelationGraph(AnitaPol::AnitaPol_t pol, Int_t ant) const
virtual UsefulAnitaEvent * useful(bool force_reload=false)
void initTemplate(const FilteredAnitaEvent *fEv)
const AnalysisWaveform * getRawGraph(UInt_t i) const
Adu5Pat * gps(bool force_reload=false)
const AnalysisWaveform * getFilteredGraph(UInt_t i) const
virtual RawAnitaHeader * header(bool force_reload=false)
const TGraphAligned * even() const
Horizontal Polarisation.
This class is intended to store all the necessary data about an ANITA event for filtering and analysi...
enum AnitaPol::EAnitaPol AnitaPol_t
Polarisation enumeration.
This class is intended to be the main storage vessel for ANITA waveforms. It is similar in principle ...
const RawAnitaHeader * getHeader() const