FFTIndexing.jl is a small package I’ve written that provides a few types that you can use to index an array in a manner that exposes the underlying frequency bins from a Fourier transform.

This package accomplishes similar goals to FFTViews.jl, but does so without constructing any view objects. Instead, it provides types, `FFTIndex`

and `FFTIndices`

, similar to `CartesianIndex`

and `CartesianIndices`

in Julia Base, that can be used with any array that defines `getindex`

and/or `setindex!`

.

## Usage

An index `i::FFTIndex{D}`

type indexes an array `A::AbstractArray{T,D}`

with the assumption that the array has periodic boundary conditions. Suppose `A`

is a `Array{Float32,3}`

which resulted from a multidimensional fast Fourier transform: `FFTIndex(0, 0, 0)`

corresponds to the zero frequency component, located at `firstindex(A)`

, and `FFTIndex(-1, -1, -1)`

corresponds to the last index.

The array is assumed to have periodic boundary conditions, and modulo math is used to interpret values in an `FFTIndex`

as valid array indices. This allows for the elimination of bounds checks if this is the only type used to index an array. For example, if `size(A) === (3, 3, 7)`

:

```
julia> A[3, 3, 7] === A[FFTIndex(2, 2, 6)]
true
julia> A[3, 3, 7] === A[FFTIndex(-1, -1, -1)]
true
```

This also works for disparate `FFTIndex`

dimensionalities, as long as the total dimensions indexed is equal to that of the array:

```
julia> A[3, 3, 7] === A[FFTIndex(2, 2), FFTIndex(6)]
true
```

The `FFTIndices{D}`

type represents all of the valid `FFTIndex{D}`

objects for a given array or other object that has a `size`

.

## Use case

In my research, I’ve needed to take fast Fourier transforms of datasets (which are `Vector{Float32}`

) of disparate length. Using this package, I can combine `FFTIndices`

with `stack`

to fit all of the data into a contiguous `Matrix{Float32}`

rather than a `Vector{Vector{Float32}}`

:

```
julia> stack(v -> fft(v)[FFTIndices((256,))] for v in data)
```

This automatically truncates the high frequency components of longer datasets down to a fixed size so they all fit into the matrix.