NCFS-Pack
A generic (astro)particle physics analysis framework
 
Loading...
Searching...
No Matches
NcTransform.cxx
Go to the documentation of this file.
1
31
33
129
130#include "NcTransform.h"
131#include "Riostream.h"
132
133ClassImp(NcTransform); // Class implementation to enable ROOT I/O
134
136NcTransform::NcTransform(const char* name,const char* title) : TNamed(name,title)
137{
143
144 Reset();
145 fSample=0;
146}
147
149{
155
156 if (fProc)
157 {
158 delete fProc;
159 fProc=0;
160 }
161}
162
164{
170
171 fProc=0;
172 fN=q.fN;
173 fReIn=q.fReIn;
174 fImIn=q.fImIn;
175 fReOut=q.fReOut;
176 fImOut=q.fImOut;
178}
179
181{
187
188 fProc=0;
189 fN=0;
190 fReIn.Set(0);
191 fImIn.Set(0);
192 fReOut.Set(0);
193 fImOut.Set(0);
194}
195
197{
206
207 fSample=f;
208}
209
211{
217
218 return fSample;
219}
220
221void NcTransform::Load(Int_t n,Double_t* re,Double_t* im,Float_t f)
222{
240
241 Reset();
242
243 if (f>=0) fSample=f;
244
245 if (n<1) return;
246
247 fN=n;
248 if (re) fReIn.Set(n);
249 if (im) fImIn.Set(n);
250
251 for (Int_t i=0; i<n; i++)
252 {
253 if (re) fReIn.SetAt(re[i],i);
254 if (im) fImIn.SetAt(im[i],i);
255 }
256}
257
258void NcTransform::Load(TArray* re,TArray* im,Float_t f)
259{
277
278 Reset();
279
280 if (f>=0) fSample=f;
281
282 Int_t nre=0;
283 Int_t nim=0;
284 if (re) nre=re->GetSize();
285 if (im) nim=im->GetSize();
286
287 Int_t n=nre;
288 if (!n) n=nim;
289 if (nre && nim>nre) n=nre;
290 if (nim && nre>nim) n=nim;
291
292 if (n<1) return;
293
294 fN=n;
295 if (nre) fReIn.Set(n);
296 if (nim) fImIn.Set(n);
297
298 Double_t valre=0;
299 Double_t valim=0;
300 for (Int_t i=0; i<n; i++)
301 {
302 if (nre)
303 {
304 valre=re->GetAt(i);
305 fReIn.SetAt(valre,i);
306 }
307 if (nim)
308 {
309 valim=im->GetAt(i);
310 fImIn.SetAt(valim,i);
311 }
312 }
313}
314
315void NcTransform::Load(NcSample* s,Int_t i,Float_t f)
316{
332
333 Reset();
334
335 if (f>=0) fSample=f;
336
337 if (!s)
338 {
339 cout << " *" << ClassName() <<"::Load* No input sample specified." << endl;
340 return;
341 }
342
343 Int_t n=s->GetN();
344 Int_t store=s->GetStoreMode();
345 Int_t dim=s->GetDimension();
346
347 if (n<1 || !store || dim<1 || i<1 || i>dim)
348 {
349 cout << " *" << ClassName() <<"::Load* Inconsistent input for NcSample treatment." << endl;
350 cout << " Store Mode:" << store << " Entries:" << n << " Dimension:" << dim << " i:" << i << " f:" << fSample << endl;
351 return;
352 }
353
354 fN=n;
355 fReIn.Set(n);
356
357 Double_t val=0;
358 for (Int_t idx=1; idx<=n; idx++)
359 {
360 val=s->GetEntry(idx,i);
361 fReIn.SetAt(val,idx-1);
362 }
363}
364
365void NcTransform::Load(NcSample* s,TString name,Float_t f)
366{
382
383 Reset();
384
385 if (f>=0) fSample=f;
386
387 if (!s)
388 {
389 cout << " *" << ClassName() <<"::Load* No input sample specified." << endl;
390 return;
391 }
392
393 Int_t n=s->GetN();
394 Int_t store=s->GetStoreMode();
395 Int_t dim=s->GetDimension();
396 Int_t i=s->GetIndex(name);
397
398
399 if (n<1 || !store || dim<1 || !i)
400 {
401 cout << " *" << ClassName() <<"::Load* Inconsistent input for NcSample treatment." << endl;
402 cout << " Store Mode:" << store << " Entries:" << n << " Dimension:" << dim << " name:" << name << " f:" << fSample << endl;
403 return;
404 }
405
406 Load(s,i,f);
407}
408
409void NcTransform::Load(TH1* h,Float_t f)
410{
424
425 Reset();
426
427 if (f>=0) fSample=f;
428
429 if (!h)
430 {
431 cout << " *" << ClassName() <<"::Load* No input histogram specified." << endl;
432 return;
433 }
434
435 Int_t nbins=h->GetNbinsX();
436 Double_t nentries=h->GetEntries();
437
438 if (!nbins || !nentries)
439 {
440 cout << " *" << ClassName() <<"::Load* Inconsistent input for histogram treatment." << endl;
441 cout << " Nbins:" << nbins << " Nentries:" << nentries << " f:" << fSample << endl;
442 return;
443 }
444
445 fN=nbins;
446 fReIn.Set(nbins);
447
448 Double_t val=0;
449 for (Int_t i=1; i<=nbins; i++)
450 {
451 val=h->GetBinContent(i);
452 fReIn.SetAt(val,i-1);
453 }
454}
455
456void NcTransform::Load(TGraph* gr,Float_t f)
457{
471
472 Reset();
473
474 if (f>=0) fSample=f;
475
476 if (!gr)
477 {
478 cout << " *" << ClassName() <<"::Load* No input TGraph object specified." << endl;
479 return;
480 }
481
482 Int_t n=gr->GetN();
483
484 if (!n)
485 {
486 cout << " *" << ClassName() <<"::Load* Inconsistent input for TGraph treatment." << endl;
487 cout << " n:" << n << " f:" << fSample << endl;
488 return;
489 }
490
491 fN=n;
492 fReIn.Set(n);
493
494 gr->Sort();
495
496 Double_t x=0;
497 Double_t y=0;
498 for (Int_t i=0; i<n; i++)
499 {
500 gr->GetPoint(i,x,y);
501 fReIn.SetAt(y,i);
502 }
503}
504
506{
513
516 fReOut.Set(0);
517 fImOut.Set(0);
518}
519
520Int_t NcTransform::GetN() const
521{
527
528 return fN;
529}
530
531TArrayD NcTransform::GetData(TString sel) const
532{
554
555 if (sel.Contains("RE") && sel.Contains("in")) return fReIn;
556 if (sel.Contains("IM") && sel.Contains("in")) return fImIn;
557 if (sel.Contains("RE") && sel.Contains("out")) return fReOut;
558 if (sel.Contains("IM") && sel.Contains("out")) return fImOut;
559
560 TArrayD data(fN);
561 Double_t pi=acos(-1.);
562 Double_t re=0;
563 Double_t im=0;
564 Double_t amp=0;
565 Double_t phi=0;
566 for (Int_t i=0; i<fN; i++)
567 {
568 if (sel.Contains("in"))
569 {
570 re=fReIn.At(i);
571 im=fImIn.At(i);
572 }
573 if (sel.Contains("out"))
574 {
575 re=fReOut.At(i);
576 im=fImOut.At(i);
577 }
578 amp=sqrt(re*re+im*im);
579 phi=0;
580 if (im || re) phi=atan2(im,re);
581
582 if (sel.Contains("AMP")) data.SetAt(amp,i);
583 if (sel.Contains("PHIR")) data.SetAt(phi,i);
584 if (sel.Contains("PHID")) data.SetAt(phi*180./pi,i);
585 }
586
587 return data;
588}
589
590void NcTransform::Fourier(TString mode,TH1* hist,TString sel)
591{
637
638 fReOut.Set(0);
639 fImOut.Set(0);
640
641 if (fN<1) return;
642
643 Int_t n=1+fN/2;
644 Float_t maxfrac=0.5;
645 if (sel.Contains("n") || sel.Contains("t") || sel.Contains("2"))
646 {
647 n=fN;
648 maxfrac=1;
649 }
650
651 // Construct the Fast Fourier Transform (FFT) processor
652 TString opt=mode;
653 // Comply with the TVirtualFFT conventions
654 if (mode=="C2C") opt="C2CFORWARD";
655 if (mode=="C2CI") opt="C2CBACKWARD";
656 // Set the optimalisation initialisation to "estimate" and create a new processor
657 opt+=" ES K";
658
659 if (fProc)
660 {
661 delete fProc;
662 fProc=0;
663 }
664
665 fProc=TVirtualFFT::FFT(1,&fN,opt);
666
667 // Enter the input data
668 Int_t nReIn=fReIn.GetSize();
669 Int_t nImIn=fImIn.GetSize();
670 if (mode=="R2C")
671 {
672 Double_t* data=fReIn.GetArray();
673 fProc->SetPoints(data);
674 }
675 else
676 {
677 for (Int_t i=0; i<fN; i++)
678 {
679 if (nReIn && nImIn) fProc->SetPoint(i,fReIn[i],fImIn[i]);
680 if (nReIn && !nImIn) fProc->SetPoint(i,fReIn[i],0);
681 if (!nReIn && nImIn) fProc->SetPoint(i,0,fImIn[i]);
682 }
683 }
684
685 // Perform the Fast Fourier Transform
686 fProc->Transform();
687
688 Double_t rN=fN;
689
690 // Copy the resulting data in the output arrays
691 fReOut.Set(fN);
692 fImOut.Set(fN);
693 Double_t re=0;
694 Double_t im=0;
695 for (Int_t i=0; i<fN; i++)
696 {
697 fProc->GetPointComplex(i,re,im);
698 re/=sqrt(rN);
699 im/=sqrt(rN);
700 fReOut.SetAt(re,i);
701 fImOut.SetAt(im,i);
702 }
703
704 if (!hist) return;
705
706 if ((sel.Contains("Hz") || sel.Contains("t")) && fSample<=0) return;
707
708 // Initialize the histogram title
709 TString title="";
710 if (mode=="C2R" || mode=="C2CI") title+="Inverse ";
711 title+="DFT (";
712 title+=mode;
713 title+=") ";
714
715 TString title2="";
716
717 // Define and fill the requested result histogram
718 if (sel.Contains("k"))
719 {
720 hist->SetBins(n,0,n-1);
721 title+="index frequency domain";
722 if (mode=="C2R" || mode=="C2CI")
723 {
724 title+=" (input)";
725 }
726 else if (fSample>0)
727 {
728 title2.Form(" (DAQ: %-.3g samples/sec)",fSample);
729 title+=title2;
730 }
731 title+=";Index k";
732 if (sel.Contains("RE")) title+=";Re(Q[k])";
733 if (sel.Contains("IM")) title+=";Im(Q[k])";
734 if (sel.Contains("AMP")) title+=";Amplitude |Q[k]|";
735 if (sel.Contains("PHIR")) title+=";Phase #varphi[k] (rad)";
736 if (sel.Contains("PHID")) title+=";Phase #varphi[k] (deg)";
737 }
738 if (sel.Contains("f"))
739 {
740 hist->SetBins(n,0,maxfrac);
741 title+="fractional frequency domain";
742 if (mode=="C2R" || mode=="C2CI")
743 {
744 title+=" (input)";
745 }
746 else if (fSample>0)
747 {
748 title2.Form(" (DAQ: %-.3g samples/sec)",fSample);
749 title+=title2;
750 }
751 title+=";Fraction f of sampling rate";
752 if (sel.Contains("RE")) title+=";Re(Q[f])";
753 if (sel.Contains("IM")) title+=";Im(Q[f])";
754 if (sel.Contains("AMP")) title+=";Amplitude |Q[f]|";
755 if (sel.Contains("PHIR")) title+=";Phase #varphi[f] (rad)";
756 if (sel.Contains("PHID")) title+=";Phase #varphi[f] (deg)";
757 }
758 if (sel.Contains("Hz"))
759 {
760 hist->SetBins(n,0,maxfrac*fSample);
761 title+="actual frequency domain";
762 if (mode=="C2R" || mode=="C2CI")
763 {
764 title+=" (input)";
765 }
766 else if (fSample>0)
767 {
768 title2.Form(" (DAQ: %-.3g samples/sec)",fSample);
769 title+=title2;
770 }
771 title+=";Frequency #nu (Hz)";
772 if (sel.Contains("RE")) title+=";Re(Q[#nu])";
773 if (sel.Contains("IM")) title+=";Im(Q[#nu])";
774 if (sel.Contains("AMP")) title+=";Amplitude |Q[#nu]|";
775 if (sel.Contains("PHIR")) title+=";Phase #varphi[#nu] (rad)";
776 if (sel.Contains("PHID")) title+=";Phase #varphi[#nu] (deg)";
777 }
778
779 if (sel.Contains("n"))
780 {
781 hist->SetBins(fN,0,fN);
782 title+="sampling time domain";
783 if (mode=="R2C" || mode=="C2C") title+=" input";
784 if (fSample>0) title2.Form(" (%-.3g samples/sec)",fSample);
785 title+=title2;
786 title+=";Sample number n";
787 if (mode=="R2C" || mode=="C2R")
788 {
789 title+=";Value X[n]";
790 }
791 else
792 {
793 if (sel.Contains("RE")) title+=";Re(X[n])";
794 if (sel.Contains("IM")) title+=";Im(X[n])";
795 if (sel.Contains("AMP")) title+=";Amplitude |X[n]|";
796 if (sel.Contains("PHIR")) title+=";Phase #varphi[n] (rad)";
797 if (sel.Contains("PHID")) title+=";Phase #varphi[n] (deg)";
798 }
799 }
800 if (sel.Contains("t"))
801 {
802 hist->SetBins(fN,0,rN/fSample);
803 title+="actual time domain";
804 if (mode=="R2C" || mode=="C2C") title+=" input";
805 if (fSample>0) title2.Form(" (%-.3g samples/sec)",fSample);
806 title+=title2;
807 title+=";Time t (seconds)";
808 if (mode=="R2C" || mode=="C2R")
809 {
810 title+=";Value X[t]";
811 }
812 else
813 {
814 if (sel.Contains("RE")) title+=";Re(X[t])";
815 if (sel.Contains("IM")) title+=";Im(X[t])";
816 if (sel.Contains("AMP")) title+=";Amplitude |X[t]|";
817 if (sel.Contains("PHIR")) title+=";Phase #varphi[t] (rad)";
818 if (sel.Contains("PHID")) title+=";Phase #varphi[t] (deg)";
819 }
820 }
821
822 hist->SetTitle(title);
823
824 Double_t pi=acos(-1.);
825 Double_t amp=0;
826 Double_t phi=0;
827 re=0;
828 im=0;
829 for (Int_t i=0; i<n; i++)
830 {
831 if (sel.Contains("n") || sel.Contains("t")) // Time domain data requested
832 {
833 if (mode=="R2C")
834 {
835 if (nReIn) hist->SetBinContent(i+1,fReIn.At(i));
836 continue;
837 }
838 if (mode=="C2R")
839 {
840 hist->SetBinContent(i+1,fReOut.At(i));
841 continue;
842 }
843 if (mode=="C2C")
844 {
845 if (nReIn) re=fReIn.At(i);
846 if (nImIn) im=fImIn.At(i);
847 }
848 if (mode=="C2CI")
849 {
850 re=fReOut.At(i);
851 im=fImOut.At(i);
852 }
853 }
854 else // Frequency domain data requested
855 {
856 if (mode=="C2R" || mode=="C2CI") // Inverse transformation
857 {
858 if (nReIn) re=fReIn.At(i);
859 if (nImIn) im=fImIn.At(i);
860 }
861 else // Forward transformation
862 {
863 re=fReOut.At(i);
864 im=fImOut.At(i);
865 }
866 }
867 amp=sqrt(re*re+im*im);
868 phi=0;
869 if (im || re) phi=atan2(im,re);
870
871 if (sel.Contains("RE")) hist->SetBinContent(i+1,re);
872 if (sel.Contains("IM")) hist->SetBinContent(i+1,im);
873 if (sel.Contains("AMP")) hist->SetBinContent(i+1,amp);
874 if (sel.Contains("PHIR")) hist->SetBinContent(i+1,phi);
875 if (sel.Contains("PHID")) hist->SetBinContent(i+1,phi*180./pi);
876 }
877}
878
879void NcTransform::Hartley(Int_t mode,TH1* hist,TString sel)
880{
930
931 fReOut.Set(0);
932 fImOut.Set(0);
933
934 if (!mode || fN<1) return;
935
936 Int_t n=1+fN/2;
937 Float_t maxfrac=0.5;
938 if (sel.Contains("n") || sel.Contains("t") || sel.Contains("2"))
939 {
940 n=fN;
941 maxfrac=1;
942 }
943
944 // Construct the Fast Fourier Transform (FFT) processor
945 if (fProc)
946 {
947 delete fProc;
948 fProc=0;
949 }
950
951 fProc=TVirtualFFT::FFT(1,&fN,"DHT ES K");
952
953 // Enter the input data
954 Double_t* data=fReIn.GetArray();
955 fProc->SetPoints(data);
956
957 // Perform the Discrete Hartley Transform
958 fProc->Transform();
959
960 Double_t rN=fN;
961
962 // Copy the resulting data in the output arrays
963 fReOut.Set(fN);
964 fImOut.Set(0);
965 Double_t re=0;
966 for (Int_t i=0; i<fN; i++)
967 {
968 re=fProc->GetPointReal(i,kFALSE);
969 re/=sqrt(rN);
970 fReOut.SetAt(re,i);
971 }
972
973 if (!hist) return;
974
975 if ((sel.Contains("Hz") || sel.Contains("t")) && fSample<=0) return;
976
977 // Initialize the histogram title
978 TString title="";
979 if (mode<0) title+="Inverse ";
980 title+="DHT ";
981
982 TString title2="";
983
984 // Define and fill the requested result histogram
985 if (sel.Contains("k"))
986 {
987 hist->SetBins(n,0,n-1);
988 title+="index frequency domain";
989 if (mode<0)
990 {
991 title+=" (input)";
992 }
993 else if (fSample>0)
994 {
995 title2.Form(" (DAQ: %-.3g samples/sec)",fSample);
996 title+=title2;
997 }
998 title+=";Index k;Q[k]";
999 }
1000 if (sel.Contains("f"))
1001 {
1002 hist->SetBins(n,0,maxfrac);
1003 title+="fractional frequency domain";
1004 if (mode<0)
1005 {
1006 title+=" (input)";
1007 }
1008 else if (fSample>0)
1009 {
1010 title2.Form(" (DAQ: %-.3g samples/sec)",fSample);
1011 title+=title2;
1012 }
1013 title+=";Fraction f of sampling rate;Q[f]";
1014 }
1015 if (sel.Contains("Hz"))
1016 {
1017 hist->SetBins(n,0,maxfrac*fSample);
1018 title+="actual frequency domain";
1019 if (mode<0)
1020 {
1021 title+=" (input)";
1022 }
1023 else if (fSample>0)
1024 {
1025 title2.Form(" (DAQ: %-.3g samples/sec)",fSample);
1026 title+=title2;
1027 }
1028 title+=";Frequency #nu (Hz);Q[#nu]";
1029 }
1030
1031 if (sel.Contains("n"))
1032 {
1033 hist->SetBins(fN,0,fN);
1034 title+="sampling time domain";
1035 if (mode>0) title+=" input";
1036 if (fSample>0) title2.Form(" (%-.3g samples/sec)",fSample);
1037 title+=title2;
1038 title+=";Sample number n;Value X[n]";
1039 }
1040 if (sel.Contains("t"))
1041 {
1042 hist->SetBins(fN,0,rN/fSample);
1043 title+="actual time domain";
1044 if (mode>0) title+=" input";
1045 if (fSample>0) title2.Form(" (%-.3g samples/sec)",fSample);
1046 title+=title2;
1047 title+=";Time t (seconds);Value X[t]";
1048 }
1049
1050 hist->SetTitle(title);
1051
1052 for (Int_t i=0; i<n; i++)
1053 {
1054 if (mode>0) // Forward transform
1055 {
1056 if (sel.Contains("n") || sel.Contains("t"))
1057 {
1058 hist->SetBinContent(i+1,fReIn.At(i));
1059 }
1060 else
1061 {
1062 hist->SetBinContent(i+1,fReOut.At(i));
1063 }
1064 }
1065 else // Backward transform
1066 {
1067 if (sel.Contains("n") || sel.Contains("t"))
1068 {
1069 hist->SetBinContent(i+1,fReOut.At(i));
1070 }
1071 else
1072 {
1073 hist->SetBinContent(i+1,fReIn.At(i));
1074 }
1075 }
1076 }
1077}
1078
1079void NcTransform::Cosine(Int_t type,TH1* hist,TString sel)
1080{
1134
1135 fReOut.Set(0);
1136 fImOut.Set(0);
1137
1138 if (abs(type)<1 || abs(type)>4 || fN<1 || (abs(type)==1 && fN<2)) return;
1139
1140 // Convert negative type specifications to the corresponding "normal" ones
1141 Int_t type2=type;
1142 if (type==-1 || type==-4) type2=abs(type);
1143 if (type==-2) type2=3;
1144 if (type==-3) type2=2;
1145
1146 Int_t n=1+fN/2;
1147 Float_t maxfrac=0.5;
1148 if (sel.Contains("n") || sel.Contains("t") || sel.Contains("2"))
1149 {
1150 n=fN;
1151 maxfrac=1;
1152 }
1153
1154 // Comply with the TVirtualFFT conventions
1155 Int_t kind=type2-1;
1156
1157 // Construct the Fast Fourier Transform (FFT) processor
1158 if (fProc)
1159 {
1160 delete fProc;
1161 fProc=0;
1162 }
1163
1164 fProc=TVirtualFFT::SineCosine(1,&fN,&kind,"ES");
1165
1166 // Enter the input data
1167 Double_t* data=fReIn.GetArray();
1168 fProc->SetPoints(data);
1169
1170 // Perform the Discrete Cosine Transform
1171 fProc->Transform();
1172
1173 Double_t rN=fN;
1174
1175 // Copy the resulting data in the output arrays
1176 fReOut.Set(fN);
1177 fImOut.Set(0);
1178 Double_t re=0;
1179 for (Int_t i=0; i<fN; i++)
1180 {
1181 re=fProc->GetPointReal(i,kFALSE);
1182 if (type2==1)
1183 {
1184 re/=sqrt(2.*(rN-1.));
1185 }
1186 else
1187 {
1188 re/=sqrt(2.*rN);
1189 }
1190 fReOut.SetAt(re,i);
1191 }
1192
1193 if (!hist) return;
1194
1195 if ((sel.Contains("Hz") || sel.Contains("t")) && fSample<=0) return;
1196
1197 // Initialize the histogram title
1198 TString title="";
1199 if (type<0) title+="Inverse ";
1200 title+="DCT-";
1201 if (abs(type)==1) title+="I";
1202 if (abs(type)==2) title+="II";
1203 if (abs(type)==3) title+="III";
1204 if (abs(type)==4) title+="IV";
1205 title+=" ";
1206
1207 TString title2="";
1208
1209 // Define and fill the requested result histogram
1210 if (sel.Contains("k"))
1211 {
1212 hist->SetBins(n,0,n-1);
1213 title+="index frequency domain";
1214 if (type<0)
1215 {
1216 title+=" (input)";
1217 }
1218 else if (fSample>0)
1219 {
1220 title2.Form(" (DAQ: %-.3g samples/sec)",fSample);
1221 title+=title2;
1222 }
1223 title+=";Index k;Q[k]";
1224 }
1225 if (sel.Contains("f"))
1226 {
1227 hist->SetBins(n,0,maxfrac);
1228 title+="fractional frequency domain";
1229 if (type<0)
1230 {
1231 title+=" (input)";
1232 }
1233 else if (fSample>0)
1234 {
1235 title2.Form(" (DAQ: %-.3g samples/sec)",fSample);
1236 title+=title2;
1237 }
1238 title+=";Fraction f of sampling rate;Q[f]";
1239 }
1240 if (sel.Contains("Hz"))
1241 {
1242 hist->SetBins(n,0,maxfrac*fSample);
1243 title+="actual frequency domain";
1244 if (type<0)
1245 {
1246 title+=" (input)";
1247 }
1248 else if (fSample>0)
1249 {
1250 title2.Form(" (DAQ: %-.3g samples/sec)",fSample);
1251 title+=title2;
1252 }
1253 title+=";Frequency #nu (Hz);Q[#nu]";
1254 }
1255
1256 if (sel.Contains("n"))
1257 {
1258 hist->SetBins(fN,0,fN);
1259 title+="sampling time domain";
1260 if (type>0) title+=" input";
1261 if (fSample>0) title2.Form(" (%-.3g samples/sec)",fSample);
1262 title+=title2;
1263 title+=";Sample number n;Value X[n]";
1264 }
1265 if (sel.Contains("t"))
1266 {
1267 hist->SetBins(fN,0,rN/fSample);
1268 title+="actual time domain";
1269 if (type>0) title+=" input";
1270 if (fSample>0) title2.Form(" (%-.3g samples/sec)",fSample);
1271 title+=title2;
1272 title+=";Time t (seconds);Value X[t]";
1273 }
1274
1275 hist->SetTitle(title);
1276
1277 // Determine stepsize in fractional sampling frequency
1278 Double_t fstep=1./(2.*rN);
1279 if (type==1) fstep=1./(2.*double(fN-1));
1280
1281 Double_t x=0;
1282 for (Int_t i=0; i<n; i++)
1283 {
1284 x=i;
1285 if (type2==3 || type2==4) x+=0.5;
1286 x*=fstep;
1287
1288 if (sel.Contains("n") || sel.Contains("t"))
1289 {
1290 if (type>0)
1291 {
1292 hist->SetBinContent(i+1,fReIn.At(i));
1293 }
1294 else
1295 {
1296 hist->SetBinContent(i+1,fReOut.At(i));
1297 }
1298 }
1299 else if (sel.Contains("k"))
1300 {
1301 if (type>0)
1302 {
1303 hist->SetBinContent(i+1,fReOut.At(i));
1304 }
1305 else
1306 {
1307 hist->SetBinContent(i+1,fReIn.At(i));
1308 }
1309 }
1310 else if (sel.Contains("f"))
1311 {
1312 if (type>0)
1313 {
1314 hist->Fill(x,fReOut.At(i));
1315 }
1316 else
1317 {
1318 hist->Fill(x,fReIn.At(i));
1319 }
1320 }
1321 else
1322 {
1323 x*=fSample;
1324 if (type>0)
1325 {
1326 hist->Fill(x,fReOut.At(i));
1327 }
1328 else
1329 {
1330 hist->Fill(x,fReIn.At(i));
1331 }
1332 }
1333 }
1334}
1335
1336void NcTransform::Sine(Int_t type,TH1* hist,TString sel)
1337{
1389
1390 fReOut.Set(0);
1391 fImOut.Set(0);
1392
1393 if (abs(type)<1 || abs(type)>4 || fN<1 || (abs(type)==1 && fN<2)) return;
1394
1395 // Convert negative type specifications to the corresponding "normal" ones
1396 Int_t type2=type;
1397 if (type==-1 || type==-4) type2=abs(type);
1398 if (type==-2) type2=3;
1399 if (type==-3) type2=2;
1400
1401 Int_t n=1+fN/2;
1402 Float_t maxfrac=0.5;
1403 if (sel.Contains("n") || sel.Contains("t") || sel.Contains("2"))
1404 {
1405 n=fN;
1406 maxfrac=1;
1407 }
1408
1409 // Comply with the TVirtualFFT conventions
1410 Int_t kind=type2+3;
1411
1412 // Construct the Fast Fourier Transform (FFT) processor
1413 if (fProc)
1414 {
1415 delete fProc;
1416 fProc=0;
1417 }
1418
1419 fProc=TVirtualFFT::SineCosine(1,&fN,&kind,"ES K");
1420
1421 // Enter the input data
1422 Double_t* data=fReIn.GetArray();
1423 fProc->SetPoints(data);
1424
1425 // Perform the Discrete Cosine Transform
1426 fProc->Transform();
1427
1428 Double_t rN=fN;
1429
1430 // Copy the resulting data in the output arrays
1431 fReOut.Set(fN);
1432 fImOut.Set(0);
1433 Double_t re=0;
1434 for (Int_t i=0; i<fN; i++)
1435 {
1436 re=fProc->GetPointReal(i,kFALSE);
1437 if (type2==1)
1438 {
1439 re/=sqrt(2.*(rN+1.));
1440 }
1441 else
1442 {
1443 re/=sqrt(2.*rN);
1444 }
1445 fReOut.SetAt(re,i);
1446 }
1447
1448 if (!hist) return;
1449
1450 if ((sel.Contains("Hz") || sel.Contains("t")) && fSample<=0) return;
1451
1452 // Initialize the histogram title
1453 TString title="";
1454 if (type<0) title+="Inverse ";
1455 title+="DST-";
1456 if (abs(type)==1) title+="I";
1457 if (abs(type)==2) title+="II";
1458 if (abs(type)==3) title+="III";
1459 if (abs(type)==4) title+="IV";
1460 title+=" ";
1461
1462 TString title2="";
1463
1464 // Define and fill the requested result histogram
1465 if (sel.Contains("k"))
1466 {
1467 hist->SetBins(n,0,n-1);
1468 title+="index frequency domain";
1469 if (type<0)
1470 {
1471 title+=" (input)";
1472 }
1473 else if (fSample>0)
1474 {
1475 title2.Form(" (DAQ: %-.3g samples/sec)",fSample);
1476 title+=title2;
1477 }
1478 title+=";Index k;Q[k]";
1479 }
1480 if (sel.Contains("f"))
1481 {
1482 hist->SetBins(n,0,maxfrac);
1483 title+="fractional frequency domain";
1484 if (type<0)
1485 {
1486 title+=" (input)";
1487 }
1488 else if (fSample>0)
1489 {
1490 title2.Form(" (DAQ: %-.3g samples/sec)",fSample);
1491 title+=title2;
1492 }
1493 title+=";Fraction f of sampling rate;Q[f]";
1494 }
1495 if (sel.Contains("Hz"))
1496 {
1497 hist->SetBins(n,0,maxfrac*fSample);
1498 title+="actual frequency domain";
1499 if (type<0)
1500 {
1501 title+=" (input)";
1502 }
1503 else if (fSample>0)
1504 {
1505 title2.Form(" (DAQ: %-.3g samples/sec)",fSample);
1506 title+=title2;
1507 }
1508 title+=";Frequency #nu (Hz);Q[#nu]";
1509 }
1510
1511 if (sel.Contains("n"))
1512 {
1513 hist->SetBins(fN,0,fN);
1514 title+="sampling time domain";
1515 if (type>0) title+=" input";
1516 if (fSample>0) title2.Form(" (%-.3g samples/sec)",fSample);
1517 title+=title2;
1518 title+=";Sample number n;Value X[n]";
1519 }
1520 if (sel.Contains("t"))
1521 {
1522 hist->SetBins(fN,0,rN/fSample);
1523 title+="actual time domain";
1524 if (type>0) title+=" input";
1525 if (fSample>0) title2.Form(" (%-.3g samples/sec)",fSample);
1526 title+=title2;
1527 title+=";Time t (seconds);Value X[t]";
1528 }
1529
1530 hist->SetTitle(title);
1531
1532 // Determine stepsize in fractional sampling frequency
1533 Double_t fstep=1./(2.*rN);
1534 if (type==1) fstep=1./(2.*double(fN+1));
1535
1536 Double_t x=0;
1537 for (Int_t i=0; i<n; i++)
1538 {
1539 x=i+1;
1540 if (type2==3 || type2==4) x-=0.5;
1541 x*=fstep;
1542
1543 if (sel.Contains("n") || sel.Contains("t"))
1544 {
1545 if (type>0)
1546 {
1547 hist->SetBinContent(i+1,fReIn.At(i));
1548 }
1549 else
1550 {
1551 hist->SetBinContent(i+1,fReOut.At(i));
1552 }
1553 }
1554 else if (sel.Contains("k"))
1555 {
1556 if (type>0)
1557 {
1558 hist->SetBinContent(i+1,fReOut.At(i));
1559 }
1560 else
1561 {
1562 hist->SetBinContent(i+1,fReIn.At(i));
1563 }
1564 }
1565 else if (sel.Contains("f"))
1566 {
1567 if (type>0)
1568 {
1569 hist->Fill(x,fReOut.At(i));
1570 }
1571 else
1572 {
1573 hist->Fill(x,fReIn.At(i));
1574 }
1575 }
1576 else
1577 {
1578 x*=fSample;
1579 if (type>0)
1580 {
1581 hist->Fill(x,fReOut.At(i));
1582 }
1583 else
1584 {
1585 hist->Fill(x,fReIn.At(i));
1586 }
1587 }
1588 }
1589}
1590
1591TObject* NcTransform::Clone(const char* name) const
1592{
1602
1603 NcTransform* q=new NcTransform(*this);
1604 if (name)
1605 {
1606 if (strlen(name)) q->SetName(name);
1607 }
1608 return q;
1609}
1610
ClassImp(NcTransform)
Sampling and statistics tools for various multi-dimensional data samples.
Definition NcSample.h:28
Int_t GetStoreMode() const
Int_t GetN() const
Int_t GetIndex(TString name) const
Int_t GetDimension() const
Double_t GetEntry(Int_t i, Int_t j, Int_t mode=0, Int_t k=0)
Various transformations of (sequential) data samples.
Definition NcTransform.h:15
TArrayD GetData(TString mode) const
void SetSamplingFrequency(Float_t f)
void Load(Int_t n, Double_t *re, Double_t *im=0, Float_t f=-1)
NcTransform(const char *name="", const char *title="")
Int_t GetN() const
TVirtualFFT * fProc
Definition NcTransform.h:38
Float_t GetSamplingFrequency() const
virtual TObject * Clone(const char *name="") const
void LoadResult()
void Fourier(TString mode, TH1 *hist=0, TString sel="none")
TArrayD fImOut
Definition NcTransform.h:43
void Cosine(Int_t type, TH1 *hist=0, TString sel="none")
TArrayD fReIn
Definition NcTransform.h:40
TArrayD fImIn
Definition NcTransform.h:41
virtual ~NcTransform()
void Sine(Int_t type, TH1 *hist=0, TString sel="none")
Float_t fSample
Definition NcTransform.h:44
TArrayD fReOut
Definition NcTransform.h:42
void Hartley(Int_t mode, TH1 *hist=0, TString sel="none")