Current section
Files
Jump to
Current section
Files
lib/fft.ex
defmodule FFT do
@moduledoc """
FFT.
## Calculation of the fast fourier transform, in the first version for lists of maximum 8bits.
"""
require Integer
import :math
@doc """
solve.
Returns the fft for a list of in the max 8bits
"""
def transformer (a) do
solve(a)
end
defp solve(a, i \\ -1, s \\ 1, k \\ 0, j \\ 0) do
unless i >= (length(a)) || i == -1 do
if (pow(2, s) + j - 1) > (length(a) / 2) do
b = butterfly(Enum.at(a, i), Enum.at(a, i+1), k, pow(2, s))
a |> List.update_at(i, &(&1 = Enum.at(b, 0)))
|> List.update_at((i + 1), &(&1 = Enum.at(b, 1)))
|> solve(i + 2, s, k + 1)
else
b = butterfly(Enum.at(a, i), Enum.at(a, i + 1), k, pow(2, s))
a |> List.update_at(i, &(&1 = Enum.at(b, 0)))
|> List.update_at((i + 1), &(&1 = Enum.at(b, 1)))
|> solve(i + 2, s, k, j + 1)
end
else
if i == -1 do
a |> bit_reverse |> solve(i + 1)
else
unless s >= log2(length(a))do
a |> even_odd |> solve(0, s + 1)
else
even_odd(a)
end
end
end
end
@doc """
Bit-reverse.
Returns the fft for a list of in the max 8bits
"""
def bit_reverse(array, reverse \\ [], n \\ 0) do
unless n == length(array) do
ind = n |> Integer.digits(2)
|> zeros(array)
|> inverter
|> Integer.undigits(2)
bit_reverse(array, reverse ++ [Enum.at(array, ind)], n + 1)
else
reverse
end
end
defp butterfly(h, g, k, n) do
w = ComplexNum.new(1, (-2 * pi() * k / n), :polar)
t = ComplexNum.mult(w, g)
[ComplexNum.add(h, t), ComplexNum.sub(h, t)]
end
#defp modulus_vector(a) do
# Enum.map(a, fn x -> ComplexNum.magnitude(x) end )
#end
defp zeros(bin, a) do
len = length(bin)
unless len == :math.log2(length(a)), do: zeros([0] ++ bin, a), else: bin
end
defp inverter(bin, resp \\[]) do
[h | t] = bin
unless t == [], do: inverter(t, [h] ++ resp), else: [h] ++ resp
end
defp even_odd(a, rec \\ -1, e \\ [], o \\ [], n \\ 0) do
unless n >= length(a) do
if Integer.is_even(n),
do: even_odd(a, rec, e ++ [Enum.at(a, n)], o ,n + 1), else: even_odd(a,rec , e, o ++ [Enum.at(a, n)],n + 1)
else
if rec > 0 do
even_odd(e++o, rec - 1)
else
e++o
end
end
end
end