Skip to content

Commit 0e19f26

Browse files
committed
Mistake in real FFT
1 parent 0ff5ea0 commit 0e19f26

File tree

7 files changed

+46
-50
lines changed

7 files changed

+46
-50
lines changed

src/FFTA.jl

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -45,6 +45,13 @@ function bfft(x::AbstractVector{T}) where {T}
4545
y
4646
end
4747

48+
function bfft(x::AbstractVector{T}) where {T <: Real}
49+
y = similar(x, Complex{T})
50+
g = CallGraph{Complex{T}}(length(x))
51+
fft!(y, x, 1, 1, FFT_BACKWARD(), g[1].type, g, 1)
52+
y
53+
end
54+
4855
function bfft(x::AbstractMatrix{T}) where {T}
4956
M,N = size(x)
5057
y1 = similar(x)

src/algos.jl

Lines changed: 12 additions & 38 deletions
Original file line numberDiff line numberDiff line change
@@ -62,8 +62,7 @@ end
6262
Power of 2 FFT in place, complex
6363
6464
"""
65-
function fft_pow2!(out::AbstractVector{T}, in::AbstractVector{T}, N::Int, start_out::Int, stride_out::Int, start_in::Int, stride_in::Int, d::Direction) where {T}
66-
65+
function fft_pow2!(out::AbstractVector{T}, in::AbstractVector{U}, N::Int, start_out::Int, stride_out::Int, start_in::Int, stride_in::Int, d::Direction) where {T, U}
6766
if N == 2
6867
out[start_out] = in[start_in] + in[start_in + stride_in]
6968
out[start_out + stride_out] = in[start_in] - in[start_in + stride_in]
@@ -86,35 +85,6 @@ function fft_pow2!(out::AbstractVector{T}, in::AbstractVector{T}, N::Int, start_
8685
end
8786
end
8887

89-
"""
90-
Power of 2 FFT in place, real
91-
92-
"""
93-
function fft_pow2!(out::AbstractVector{Complex{T}}, in::AbstractVector{T}, N::Int, start_out::Int, stride_out::Int, start_in::Int, stride_in::Int, d::Direction) where {T<:Real}
94-
if N == 2
95-
out[1] = in[1] + in[2]
96-
out[2] = in[1] - in[2]
97-
return
98-
end
99-
m = N ÷ 2
100-
fft_pow2!(out, in, m, start_out , stride_out, start_in , stride_in*2, d)
101-
fft_pow2!(out, in, m, start_out + m, stride_out, start_in + 1, stride_in*2, d)
102-
103-
w1 = convert(Complex{T}, cispi(direction_sign(d)*2/N))
104-
wj = one(Complex{T})
105-
@inbounds @turbo for j in 1:m-1
106-
j1_out = start_out + j*stride_out
107-
j2_out = start_out + (j+m)*stride_out
108-
out[j1_out] = out[j1_out] + wj*out[j2_out]
109-
wj *= w1
110-
end
111-
@inbounds @turbo for j in 1:m-1
112-
j1_out = start_out + (j+m)*stride_out
113-
j2_out = start_out + (m-j+1)*stride_out
114-
out[j1_out] = conj(out[j2_out])
115-
end
116-
end
117-
11888
function fft_dft!(out::AbstractVector{T}, in::AbstractVector{T}, N::Int, start_out::Int, stride_out::Int, start_in::Int, stride_in::Int, d::Direction) where {T}
11989
tmp = in[start_in]
12090
@inbounds for j in 1:N-1
@@ -139,22 +109,26 @@ function fft_dft!(out::AbstractVector{Complex{T}}, in::AbstractVector{T}, N::Int
139109
halfN = N÷2
140110
wk = wkn = w = convert(Complex{T}, cispi(direction_sign(d)*2/N))
141111

142-
out[start_out + 1:stride_out:start_out+stride_out*N] .= in[1]
143-
out[1] = sum(@view in[start_in:stride_in:start_int+stride_out*N])
144-
iseven(N) && (out[start_out + stride_out*halfN] = alternatingSum(@view in[start_in:stride_in:start_int+stride_out*N]))
112+
tmpBegin = tmpHalf = in[start_in]
113+
@inbounds for j in 1:N-1
114+
tmpBegin += in[start_in + stride_in*j]
115+
iseven(j) ? tmpHalf += in[start_in + stride_in*j] : tmpHalf -= in[start_in + stride_in*j]
116+
end
117+
out[start_out] = convert(Complex{T}, tmpBegin)
118+
iseven(N) && (out[start_out + stride_out*halfN] = convert(Complex{T}, tmpHalf))
145119

146-
@inbounds for d in 2:halfN+1
120+
@inbounds for d in 1:halfN
147121
tmp = in[start_in]
148-
@inbounds for k in 2:N
122+
@inbounds for k in 1:N-1
149123
tmp += wkn*in[start_in + k*stride_in]
150124
wkn *= wk
151125
end
152126
out[start_out + d*stride_out] = tmp
153127
wk *= w
154128
wkn = wk
155129
end
156-
@inbounds @turbo for i in 0:halfN-1
157-
out[start_out + stride_out*(N-i)] = conj(out[start_out + stride_out*(halfN-i)])
130+
@inbounds @turbo for i in 1:halfN-1
131+
out[start_out + stride_out*(N-i)] = conj(out[start_out + stride_out*i])
158132
end
159133
end
160134

test/complex_backward.jl

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -4,8 +4,8 @@ test_nums = [8, 11, 15, 100]
44
for N in test_nums
55
x = ones(ComplexF64, N)
66
y = bfft(x)
7-
b1 = isapprox(y[1], N, atol=1e-12)
8-
b2 = isapprox(y[2:end], 0*x[2:end], atol=1e-12)
9-
@test b1 && b2
7+
y_ref = 0*y
8+
y_ref[1] = N
9+
@test y y_ref atol=1e-12
1010
end
1111
end

test/complex_forward.jl

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -2,9 +2,10 @@ using FFTA, Test
22
test_nums = [8, 11, 15, 100]
33
@testset verbose = true " forward" begin
44
for N in test_nums
5-
x = zeros(ComplexF64, N)
6-
x[1] = 1
5+
x = ones(ComplexF64, N)
76
y = fft(x)
8-
@test y ones(size(x))
7+
y_ref = 0*y
8+
y_ref[1] = N
9+
@test y y_ref atol=1e-12
910
end
1011
end

test/real_backward.jl

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
using FFTA, Test
2+
test_nums = [8, 11, 15, 100]
3+
@testset "backward" begin
4+
for N in test_nums
5+
x = ones(Float64, N)
6+
y = bfft(x)
7+
y_ref = 0*y
8+
y_ref[1] = N
9+
@test y_ref y atol=1e-12
10+
end
11+
end

test/real_forward.jl

Lines changed: 8 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,11 @@
11
using FFTA, Test
22
test_nums = [8, 11, 15, 100]
3-
@testset verbose = true "fft 1D real, size $(padnum(maximum(test_nums),N))" for N in test_nums
4-
x = zeros(Float64, N)
5-
x[1] = 1
6-
y = fft(x)
7-
@test y ones(size(x))
3+
@testset verbose = true "forward" begin
4+
for N in test_nums
5+
x = ones(Float64, N)
6+
y = fft(x)
7+
y_ref = 0*y
8+
y_ref[1] = N
9+
@test y y_ref atol=1e-12
10+
end
811
end

test/runtests.jl

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,7 @@ end
1414
include("complex_backward.jl")
1515
end
1616
@testset verbose = true "Real" begin
17-
# include("real_forward.jl")
17+
include("real_forward.jl")
1818
include("real_backward.jl")
1919
end
2020
end

0 commit comments

Comments
 (0)