tags:

views:

331

answers:

3

I know that if we have some data representing some wave, for example image line values, we can use fourier transform to get frequency function of that wave. But we have N values at points x=0...N-1 And we get only N frequencies at the output. So I want to analyze the wave everywhere in the range [0, N-1] For example at point u = 1.5. How can I do it?

A: 

It's been over 10 years since I've done any of these, but I think Matlab had some FT methods that would let you do what you wanted. At least that's what we used in our Linear Signals and DSP classes

taylonr
If they are known then I wish to implement them in C language.
maximus
Do you want to implement them for your own benefit, or because you need to use them? http://www.fftw.org/ has a library for FTs in C
taylonr
I need it. Not for my own benefit. Thank you!
maximus
+1  A: 

You need to interpolate the data for those intermediate points.

janneb
That is what I was thinking about at first. But are there any other methods of solving this problem?
maximus
Fundamentally, no. Of course, you could change your mind and decide not to analyze your data at intermediate points, in which case you don't need to interpolate.
janneb
You have to interpolate - but the result is just an "educated guess". For a better resulution in the frequency domain you also need more samples in time domain.
peterchen
@peterchen: Yes, of course. It goes without saying that interpolation can't magically invent data that didn't exist before.
janneb
+4  A: 

Computing the Fourier transform value for any frequency from a set of samples is actually quite easy:

F(w)= sum[over all sample indices k] ( f(t_k) e^(i w t_k) )

Code-wise, you do something like this:

float Fourier(float omega) {
  Complex a(0.0); // think "a is for accumulator"
  for(int k=0; k<value.size(); ++k) {
    float time= t_start + k*dt;
    float theta= omega * time;  // this is (w t_k) from above
    a+= value[k] * Complex(cos(theta), sin(theta));
  }
  return a;
} // note, I have explicitly written out e^(i theta) = cos(theta) + i sin(theta)

If you have irregular sample times, you can use a time[] vector/array along with your value[] vector/array, instead of computing the time from the index. (However, be careful, since irregularly spaced samples don't necessarily mean what you think they do! If this comment is in any way mysterious, stick with regular samples...)

The only problem is that, if you want to generate N regularly spaced frequencies based on regular samples, doing it the above way will take O(N^2) time. The Fast Fourier Transform is an algorithm that does this in O(N log N) time.

comingstorm
Drew Hall
Sorry but I didn't understand. We have function f(t), and we know its values at points t = 0..N-1. x_k = f(t_k), where t_k = k.So we have a discrete fourier transform:X_k = sum[over all sample indices n] (x_n * e^(-(k*n)*i*2Pi/N))From that equation we see that there are only N points of FT:X_k, k = 0..N-1I think you wrote an equation for the continuous case. Or may be I don't understand something?
maximus
I wrote an equation for continuous frequency -- I thought that was what you wanted. It doesn't matter that the input samples are discrete; mathematically, you treat them as impulses, plug them into the equation, and compute the result. If the samples are regularly spaced, the above formula and computation gives you a perfect natural interpolation between the frequencies computed by an FFT.
comingstorm
Interesting... I will check it! Thanks for idea)
maximus
The difference is that the regularly spaced frequencies you suggested (those computed by an FFT) are those appropriate for repeating samples -- as if you wrapped your sample into an infinitely repeating loop. This does not make sense for an arbitrary/continuous frequency; for that case, it is probably best to think of your (finite) sample set as a unique occurrence -- either isolated, or (equivalently) surrounded by an infinite sea of zero samples...
comingstorm