LAL  7.5.0.1-b72065a
ButterworthTimeSeries_source.c
Go to the documentation of this file.
1 #define CONCAT2x(a,b) a##b
2 #define CONCAT2(a,b) CONCAT2x(a,b)
3 #define STRING(a) #a
4 
5 #ifdef COMPLEX_DATA
6 # define DBLDATATYPE COMPLEX16
7 # ifdef SINGLE_PRECISION
8 # define DATATYPE COMPLEX8
9 # else
10 # define DATATYPE COMPLEX16
11 # endif
12 #else
13 # define DBLDATATYPE REAL8
14 # ifdef SINGLE_PRECISION
15 # define DATATYPE REAL4
16 # else
17 # define DATATYPE REAL8
18 # endif
19 #endif
20 
21 #define SERIESTYPE CONCAT2(DATATYPE,TimeSeries)
22 #define VECTORTYPE CONCAT2(DATATYPE,Vector)
23 #define FILTERTYPE CONCAT2(DBLDATATYPE,IIRFilter)
24 
25 #define BFUNC CONCAT2(XLALButterworth,SERIESTYPE)
26 #define LFUNC CONCAT2(XLALLowPass,SERIESTYPE)
27 #define HFUNC CONCAT2(XLALHighPass,SERIESTYPE)
28 
29 #define CFUNC CONCAT2(XLALCreate,FILTERTYPE)
30 #define DFUNC CONCAT2(XLALDestroy,FILTERTYPE)
31 
32 #define FFUNC CONCAT2(XLALIIRFilter,VECTORTYPE)
33 #define RFUNC CONCAT2(XLALIIRFilterReverse,VECTORTYPE)
34 
35 int BFUNC(SERIESTYPE *series, PassBandParamStruc *params)
36 {
37  INT4 n; /* The filter order. */
38  INT4 type; /* The pass-band type: high, low, or undeterminable. */
39  INT4 i; /* An index. */
40  INT4 j; /* Another index. */
41  REAL8 wc; /* The filter's transformed frequency. */
42 
43  /* Make sure the input pointers are non-null. */
44  if ( ! params || ! series || ! series->data || ! series->data->data )
46 
47  /* Parse the pass-band parameter structure. I separate this into a
48  local static subroutine because it's an icky mess of conditionals
49  that would clutter the logic of the main routine. */
50  type=XLALParsePassBandParamStruc(params,&n,&wc,series->deltaT);
51  if(type<0)
53 
54  /* An order n Butterworth filter has n poles spaced evenly along a
55  semicircle in the upper complex w-plane. By pairing up poles
56  symmetric across the imaginary axis, the filter gan be decomposed
57  into [n/2] filters of order 2, plus perhaps an additional order 1
58  filter. The following loop pairs up poles and applies the
59  filters with order 2. */
60  for(i=0,j=n-1;i<j;i++,j--){
61  REAL8 theta=LAL_PI*(i+0.5)/n;
62  REAL8 ar=wc*cos(theta);
63  REAL8 ai=wc*sin(theta);
64  FILTERTYPE *iirFilter=NULL;
65  COMPLEX16ZPGFilter *zpgFilter=NULL;
66 
67  /* Generate the filter in the w-plane. */
68  if(type==2){
69  zpgFilter = XLALCreateCOMPLEX16ZPGFilter(2,2);
70  if ( ! zpgFilter )
72  zpgFilter->zeros->data[0]=0.0;
73  zpgFilter->zeros->data[1]=0.0;
74  zpgFilter->gain=1.0;
75  }else{
76  zpgFilter = XLALCreateCOMPLEX16ZPGFilter(0,2);
77  if ( ! zpgFilter )
79  zpgFilter->gain=-wc*wc;
80  }
81  zpgFilter->poles->data[0]=ar;
82  zpgFilter->poles->data[0]+=ai*I;
83  zpgFilter->poles->data[1]=-ar;
84  zpgFilter->poles->data[1]+=ai*I;
85 
86  /* Transform to the z-plane and create the IIR filter. */
87  if (XLALWToZCOMPLEX16ZPGFilter(zpgFilter)<0)
88  {
91  }
92  iirFilter = CFUNC(zpgFilter);
93  if (!iirFilter)
94  {
97  }
98 
99  /* Filter the data, once each way. */
100  if (FFUNC(series->data,iirFilter)<0
101  || RFUNC(series->data,iirFilter)<0)
102  {
104  DFUNC(iirFilter);
106  }
107 
108  /* Free the filters. */
110  DFUNC(iirFilter);
111  }
112 
113  /* Next, this conditional applies the possible order 1 filter
114  corresponding to an unpaired pole on the imaginary w axis. */
115  if(i==j){
116  FILTERTYPE *iirFilter=NULL;
117  COMPLEX16ZPGFilter *zpgFilter=NULL;
118 
119  /* Generate the filter in the w-plane. */
120  if(type==2){
121  zpgFilter=XLALCreateCOMPLEX16ZPGFilter(1,1);
122  if(!zpgFilter)
124  *zpgFilter->zeros->data=0.0;
125  zpgFilter->gain=1.0;
126  }else{
127  zpgFilter=XLALCreateCOMPLEX16ZPGFilter(0,1);
128  if(!zpgFilter)
130  zpgFilter->gain=-wc*I;
131  }
132  *zpgFilter->poles->data=wc*I;
133 
134  /* Transform to the z-plane and create the IIR filter. */
135  if (XLALWToZCOMPLEX16ZPGFilter(zpgFilter)<0)
136  {
139  }
140  iirFilter=CFUNC(zpgFilter);
141  if (!iirFilter)
142  {
145  }
146 
147  /* Filter the data, once each way. */
148  if (FFUNC(series->data,iirFilter)<0
149  || RFUNC(series->data,iirFilter)<0)
150  {
152  DFUNC(iirFilter);
154  }
155 
156  /* Free the filters. */
158  DFUNC(iirFilter);
159  }
160 
161  return 0;
162 }
163 
164 int LFUNC(SERIESTYPE *series, REAL8 frequency, REAL8 amplitude, INT4 filtorder)
165 {
166  PassBandParamStruc params;
167  params.nMax = filtorder;
168  params.f1 = frequency;
169  params.a1 = amplitude;
170  params.f2 = -1;
171  params.a2 = -1;
172  if (BFUNC(series, &params) < 0)
174  return 0;
175 }
176 
177 int HFUNC(SERIESTYPE *series, REAL8 frequency, REAL8 amplitude, INT4 filtorder)
178 {
179  PassBandParamStruc params;
180  params.nMax = filtorder;
181  params.f2 = frequency;
182  params.a2 = amplitude;
183  params.f1 = -1;
184  params.a1 = -1;
185  if (BFUNC(series, &params) < 0)
187  return 0;
188 }
189 
190 #undef BFUNC
191 #undef LFUNC
192 #undef HFUNC
193 #undef CFUNC
194 #undef DFUNC
195 #undef FFUNC
196 #undef RFUNC
197 #undef SERIESTYPE
198 #undef VECTORTYPE
199 #undef FILTERTYPE
200 #undef DBLDATATYPE
201 #undef DATATYPE
202 #undef CONCAT2x
203 #undef CONCAT2
204 #undef STRING
#define FILTERTYPE
#define SERIESTYPE
int XLALWToZCOMPLEX16ZPGFilter(COMPLEX16ZPGFilter *filter)
static int XLALParsePassBandParamStruc(PassBandParamStruc *params, INT4 *n, REAL8 *wc, REAL8 deltaT)
COMPLEX16ZPGFilter * XLALCreateCOMPLEX16ZPGFilter(INT4 numZeros, INT4 numPoles)
void XLALDestroyCOMPLEX16ZPGFilter(COMPLEX16ZPGFilter *filter)
#define LAL_PI
Archimedes's constant, pi.
Definition: LALConstants.h:179
double REAL8
Double precision real floating-point number (8 bytes).
int32_t INT4
Four-byte signed integer.
#define XLAL_ERROR(...)
Macro to invoke a failure from a XLAL routine returning an integer.
Definition: XLALError.h:700
@ XLAL_EFAULT
Invalid pointer.
Definition: XLALError.h:408
@ XLAL_EFUNC
Internal function call failed bit: "or" this with existing error number.
Definition: XLALError.h:462
@ XLAL_EINVAL
Invalid argument.
Definition: XLALError.h:409
COMPLEX16 * data
Pointer to the data array.
Definition: LALDatatypes.h:177
See DATATYPE-ZPGFilter types for details.
Definition: LALDatatypes.h:930
COMPLEX16Vector * poles
Definition: LALDatatypes.h:934
COMPLEX16Vector * zeros
Definition: LALDatatypes.h:933
This structure stores data used for constructing a low- or high-pass filter: either the order and cha...
REAL8 a1
The minimal desired attenuation factors at the reference frequencies.
REAL8 a2
The minimal desired attenuation factors at the reference frequencies.
REAL8 f1
The reference frequencies of the transition band.
INT4 nMax
The maximum desired filter order (actual order may be less if specified attenuations do not require a...
REAL8 f2
The reference frequencies of the transition band.