Hi Liam, others,
You might want to hold off on merging fast-fourier-transforms branch into master, since I'm seriously considering changing the naming scheme of some of the objects and functions. See below for the reasons why.
I've committed the real FFTs to the fast-fourier-transforms branch, as well as an fft-example.lisp file. The file adds functions that can be called to run transforms similar to the examples in the manual, and could theoretically serve as test functions. I've not added them as tests yet though, because I'm not sure how to do that, or even how to automatically generate these tests.
I'm looking into the tests in the fft directory of GSL to convert them into lisp, but haven't commited anything yet.
Now, about the current interface:
One thing that I was worried about is that I'm now using keyword arguments for e.g. stride and n (which probably should be called dimension?). Is this ok with the rest of the GSLL interface?
Second, the way the objects and functions are added might not be the "nicest" way to add them. For instance, GSL defines real (single and double float) wavetables and workspaces, which, at this moment, I've added as separate objects using separate defmobject forms. Ideally, I'd like to define them in a way so that they can be constructed with (make-wavetable 'double-float :dimension x) or so, similar to make-marray, but I wasn't sure how to do that exactly. Any tips or pointers are appreciated. This would also be great for a macro with which to do non-radix-2 FFTs more efficiently: (with-fourier-transform (workspace wavetable :type '(complex double-float) :dimension 129) ;; Perform several FFTs that are all of the specified type and dimension, ;; reusing the workspace and wavetable ...)
With regard to functions, GSL has IMO a bit of an annoying naming convention, e.g. for complex transforms, there exists a "forward", "backward" and "inverse" function, as well as a "transform" function that takes a direction as parameter. For real transforms, there is only a "transform" function that does _not_ take the direction as a parameter. The reason for this is obviously tied to how real transforms are handled, but IMO makes for a terrible interface. Ideally, a user would just want to say:
(fourier-transform vector) or maybe even (forward-fourier-transform vector) (inverse-fourier-transform vector) (backward-fourier-transform vector) ;; unscaled inverse transform
and have all the details automatically sorted out. This would typically be wrapper functions around the functions that are now already in the branch.
Finally, I haven't looked into how the slices by Malcolm Reynolds work yet, but the FFTs most likely won't work properly at all on a slice. Possibly this can be solved with wrapper functions as well.
Anyway, any feedback from anyone who plans to use these FFTs, has used GSL's FFTs or just wants to put in his two bits, is welcome.
Regards, Sumant