Available transforms
PencilFFTs.Transforms
— ModuleDefines different one-dimensional FFT-based transforms.
The transforms are all subtypes of an AbstractTransform
type.
When possible, the names of the transforms are kept consistent with the functions exported by AbstractFFTs.jl
and FFTW.jl
.
Transform types
PencilFFTs.Transforms.FFT
— TypePencilFFTs.Transforms.FFT!
— TypePencilFFTs.Transforms.BFFT
— TypeBFFT()
Unnormalised backward complex-to-complex FFT.
Like AbstractFFTs.bfft
, this transform is not normalised. To obtain the inverse transform, divide the output by the length of the transformed dimension.
See also AbstractFFTs.bfft
.
PencilFFTs.Transforms.BFFT!
— TypePencilFFTs.Transforms.RFFT
— TypePencilFFTs.Transforms.RFFT!
— TypeRFFT!()
In-place version of RFFT
.
PencilFFTs.Transforms.BRFFT
— TypeBRFFT(d::Integer)
BRFFT((d1, d2, ..., dN))
Unnormalised inverse of RFFT
.
To obtain the inverse transform, divide the output by the length of the transformed dimension (of the real output array).
As described in the AbstractFFTs docs, the length of the output cannot be fully inferred from the input length. For this reason, the BRFFT
constructor accepts an optional d
argument indicating the output length.
For multidimensional datasets, a tuple of dimensions (d1, d2, ..., dN)
may also be passed. This is equivalent to passing just dN
. In this case, the last dimension (dN
) is the one that changes size between the input and output. Note that this is the opposite of FFTW.brfft
. The reason is that, in PencilFFTs, the last dimension is the one along which a complex-to-real transform is performed.
See also AbstractFFTs.brfft
.
PencilFFTs.Transforms.BRFFT!
— TypeBRFFT!(d::Integer)
BRFFT!((d1, d2, ..., dN))
In-place version of BRFFT
.
PencilFFTs.Transforms.R2R
— TypeR2R(kind)
Real-to-real transform of type kind
.
The possible values of kind
are those described in the FFTW.r2r
docs and the FFTW
manual:
discrete cosine transforms:
FFTW.REDFT00
,FFTW.REDFT01
,FFTW.REDFFT10
,FFTW.REDFFT11
discrete sine transforms:
FFTW.RODFT00
,FFTW.RODFT01
,FFTW.RODFFT10
,FFTW.RODFFT11
discrete Hartley transform:
FFTW.DHT
Note: half-complex format DFTs (FFTW.R2HC
, FFTW.HC2R
) are not currently supported.
PencilFFTs.Transforms.R2R!
— TypePencilFFTs.Transforms.NoTransform
— TypeNoTransform()
Identity transform.
Specifies that no transformation should be applied.
PencilFFTs.Transforms.NoTransform!
— TypeNoTransform!()
In-place version of NoTransform
.
Internals
What follows is used internally in PencilFFTs
.
Types
PencilFFTs.Transforms.AbstractCustomPlan
— TypeAbstractCustomPlan
Abstract type defining a custom plan, to be used as an alternative to FFTW plans (FFTW.FFTWPlan
).
The only custom plan defined in this module is IdentityPlan
. The user can define other custom plans that are also subtypes of AbstractCustomPlan
.
Note that plan
returns a subtype of either AbstractFFTs.Plan
or AbstractCustomPlan
.
PencilFFTs.Transforms.AbstractTransform
— TypeAbstractTransform
Specifies a one-dimensional FFT-based transform.
PencilFFTs.Transforms.IdentityPlan
— TypeIdentityPlan
Type of plan associated to NoTransform
.
PencilFFTs.Transforms.IdentityPlan!
— TypeIdentityPlan!
Type of plan associated to NoTransform!
.
PencilFFTs.Transforms.Plan
— TypePlan = Union{AbstractFFTs.Plan, AbstractCustomPlan}
Union type representing any plan returned by plan
.
See also AbstractCustomPlan
.
Functions
PencilFFTs.Transforms.plan
— Functionplan(transform::AbstractTransform, A, [dims];
flags=FFTW.ESTIMATE, timelimit=Inf)
Create plan to transform array A
along dimensions dims
.
If dims
is not specified, all dimensions of A
are transformed.
For FFT plans, this function wraps the AbstractFFTs.jl
and FFTW.jl
plan creation functions. For more details on the function arguments, see AbstractFFTs.plan_fft
.
PencilFFTs.Transforms.binv
— Functionbinv(transform::AbstractTransform, d::Integer)
Returns the backwards transform associated to the given transform.
The second argument must be the length of the first transformed dimension in the forward transform. It is used in particular when transform = RFFT()
, to determine the length of the inverse (complex-to-real) transform. See the AbstractFFTs.irfft
docs for details.
The backwards transform returned by this function is not normalised. The normalisation factor for a given array can be obtained by calling scale_factor
.
Example
julia> binv(Transforms.FFT(), 42)
BFFT
julia> binv(Transforms.BRFFT(9), 42)
RFFT
PencilFFTs.Transforms.scale_factor
— Functionscale_factor(transform::AbstractTransform, A, [dims = 1:ndims(A)])
Get factor required to normalise the given array after a transformation along dimensions dims
(all dimensions by default).
The array A
must have the dimensions of the transform input.
Important: the dimensions dims
must be the same that were passed to plan
.
Examples
julia> C = zeros(ComplexF32, 3, 4, 5);
julia> scale_factor(Transforms.FFT(), C)
60
julia> scale_factor(Transforms.BFFT(), C)
60
julia> scale_factor(Transforms.BFFT(), C, 2:3)
20
julia> R = zeros(Float64, 3, 4, 5);
julia> scale_factor(Transforms.RFFT(), R, 2)
4
julia> scale_factor(Transforms.RFFT(), R, 2:3)
20
julia> scale_factor(Transforms.BRFFT(8), C)
96
julia> scale_factor(Transforms.BRFFT(9), C)
108
This will fail because the input of RFFT
is real, and R
is a complex array:
julia> scale_factor(Transforms.RFFT(), C, 2:3)
ERROR: MethodError: no method matching scale_factor(::PencilFFTs.Transforms.RFFT, ::Array{ComplexF32, 3}, ::UnitRange{Int64})
PencilFFTs.Transforms.eltype_input
— Functioneltype_input(transform::AbstractTransform, real_type<:AbstractFloat)
Determine input data type for a given transform given the floating point precision of the input data.
Some transforms, such as R2R
and NoTransform
, can take both real and complex data. For those kinds of transforms, nothing
is returned.
Example
julia> eltype_input(Transforms.FFT(), Float32)
ComplexF32 (alias for Complex{Float32})
julia> eltype_input(Transforms.RFFT(), Float64)
Float64
julia> eltype_input(Transforms.R2R(FFTW.REDFT01), Float64) # nothing
julia> eltype_input(Transforms.NoTransform(), Float64) # nothing
PencilFFTs.Transforms.eltype_output
— Functioneltype_output(transform::AbstractTransform, eltype_input)
Returns the output data type for a given transform given the input type.
Throws ArgumentError
if the input data type is incompatible with the transform type.
Example
julia> eltype_output(Transforms.NoTransform(), Float32)
Float32
julia> eltype_output(Transforms.RFFT(), Float64)
ComplexF64 (alias for Complex{Float64})
julia> eltype_output(Transforms.BRFFT(4), ComplexF32)
Float32
julia> eltype_output(Transforms.FFT(), Float64)
ERROR: ArgumentError: invalid input data type for PencilFFTs.Transforms.FFT: Float64
PencilFFTs.Transforms.expand_dims
— Functionexpand_dims(transform::AbstractTransform, Val(N))
Expand a single multidimensional transform into one transform per dimension.
Example
# Expand a real-to-complex transform in 3 dimensions.
julia> expand_dims(Transforms.RFFT(), Val(3))
(RFFT, FFT, FFT)
julia> expand_dims(Transforms.BRFFT(4), Val(3))
(BFFT, BFFT, BRFFT{even})
julia> expand_dims(Transforms.NoTransform(), Val(2))
(NoTransform, NoTransform)
PencilFFTs.Transforms.is_inplace
— Functionis_inplace(transform::AbstractTransform) -> Bool
is_inplace(transforms::Vararg{AbtractTransform}) -> Union{Bool, Nothing}
Check whether a transform or a list of transforms is performed in-place.
If the list of transforms has a combination of in-place and out-of-place transforms, nothing
is returned.
Example
julia> is_inplace(Transforms.RFFT())
false
julia> is_inplace(Transforms.NoTransform!())
true
julia> is_inplace(Transforms.FFT!(), Transforms.R2R!(FFTW.REDFT01))
true
julia> is_inplace(Transforms.FFT(), Transforms.R2R(FFTW.REDFT01))
false
julia> is_inplace(Transforms.FFT(), Transforms.R2R!(FFTW.REDFT01)) === nothing
true
PencilFFTs.Transforms.kind
— Functionkind(transform::R2R)
Get kind
of real-to-real transform.
PencilFFTs.Transforms.length_output
— Functionlength_output(transform::AbstractTransform, length_in::Integer)
Returns the length of the transform output, given the length of its input.
The input and output lengths are specified in terms of the respective input and output datatypes. For instance, for real-to-complex transforms, these are respectively the length of input real data and of output complex data.