Bill,
As a follow up to
my last …
Lets use the wave
generator ( below in AFL ) to manufacture some synthetic data
…
You can see that I
purposely picked wave lengths that are powers of two … The reason is that
FFT's will of course resolve these quite well as long as you have the sample
size set to be a power of 2 which is larger then the longest wavelength.
The amplitudes and phase offsets are pretty much random.
See the attachments
…
#1 The individual
and composite ( DATA ) waves we generated
#2 The histogram or
periodogram for the FFT … Notice how it picked all wave lengths out with
very little trouble.
#3 The output
cycles which are a result of the individual cycle lengths, amplitudes and
phase offsets that the FFT detected. Notice how this is almost a
perfect match of the input. The individual waves can of course be
easily extrapolated and combined to present a picture of where the data
should go in the future.
#4 Another
generated wave this time with trend added in … Notice the effect on the
white composite line.
#5 The resulting
histogram from the FFT WITHOUT detrending the data first. Notice how
it has become "confused".
#6 The resulting
output waves now don't look much like the inputs.
#7 Same histogram
as in #5 but with detrending the data prior to invoking the FFT.
Notice how now we are back to where we should be.
#8 The resulting
output waves as we would expect them to be …
#9 Another
generated wave this time with a very high noise level ( the grey histogram
). You can see the effect it has had on the data we
manufactured.
#10 The histogram
from FFT. Notice how even though the noise levels have gone up here,
the FFT still had no real problems finding the cycles.
#11 The resulting
output waves which now look very much like the input … WITHOUT the
noise.
#12 Here I have
purposely changed the wave lengths from being powers of 2 to 7, 17, 27, 37
& 47…. Notice the effect it has had in the histogram … I had to increase
the data sample to 512 to get this resolution which is still somewhat
"muddy" … but all in all the FFT did a good job of finding the
cycles.
The other thing to
keep in mind here with this particular wave generator is that I have not
introduced any variation in wave length, amplitude or phase offset over the
life of the data sample … which in my opinion … does happen … For the
purists that don't think this happens, then I would think that they would at
least admit that non cyclic events can make it appear to DSP algorithms as
if this were the case.
rTrend =
0;
rNoise
= 0
;
dFactor =
1;
rCyc1Amp = 3;
rCyc2Amp = 5;
rCyc3Amp = 7;
rCyc4Amp = 9;
rCyc5Amp = 11;
rCyc1Len = 4;
rCyc2Len = 8;
rCyc3Len = 16;
rCyc4Len = 32;
rCyc5Len = 64;
rCyc1Phase = 72;
rCyc2Phase = 144;
rCyc3Phase = 216;
rCyc4Phase = 288;
rCyc5Phase = 360;
if (Source == "Generator" )
{
pi =
4 * atan (1 );
StartX =
1000;
Trend = (BI +
1) * rTrend * dFactor * (rCyc1Amp +
rCyc2Amp + rCyc3Amp + rCyc4Amp + rCyc5Amp) / 5 ;
Noise = (Random () - 0.5 ) * 2 * rNoise * dFactor * (rCyc1Amp +
rCyc2Amp + rCyc3Amp + rCyc4Amp + rCyc5Amp) / 5 ;
Cycle1
= cos
((BI / rCyc1Len + rCyc1Phase / 360
) * 2
* pi) * (rCyc1Amp * dFactor) + Trend * 0.2
;
Cycle2 =
cos((BI / rCyc2Len + rCyc2Phase /
360 ) * 2 * pi) * (rCyc2Amp * dFactor) + Trend *
0.2 ;
Cycle3 =
cos((BI / rCyc3Len + rCyc3Phase /
360 ) * 2 * pi) * (rCyc3Amp * dFactor) + Trend *
0.2 ;
Cycle4 =
cos((BI / rCyc4Len + rCyc4Phase /
360 ) * 2 * pi) * (rCyc4Amp * dFactor) + Trend *
0.2 ;
Cycle5 =
cos((BI / rCyc5Len + rCyc5Phase /
360 ) * 2 * pi) * (rCyc5Amp * dFactor) + Trend *
0.2 ;
CycleX = Cycle1 + Cycle2 + Cycle3 +
Cycle4 + Cycle5 + Noise;
if (PlotIt == "IP Cycles")
{
Plot (Cycle1, "C1", colorRed);
Plot (Cycle2, "C2", colorOrange);
Plot (Cycle3, "C3", colorYellow);
Plot (Cycle4, "C4", colorBrightGreen);
Plot (Cycle5, "C5", colorBlue);
Plot (CycleX, "Cx", colorWhite, styleThick );
Plot (Noise, "n", colorLightGrey, styleThick | styleHistogram);
}
Data = StartX + CycleX;
}