PSCF v1.3
cpu/FFT.h
1#ifndef PRDC_CPU_FFT_H
2#define PRDC_CPU_FFT_H
3
4/*
5* PSCF - Polymer Self-Consistent Field
6*
7* Copyright 2015 - 2025, The Regents of the University of Minnesota
8* Distributed under the terms of the GNU General Public License.
9*/
10
11#include <prdc/cpu/RField.h>
12#include <prdc/cpu/RFieldDft.h>
13#include <prdc/cpu/CField.h>
14#include <pscf/math/IntVec.h>
15#include <util/global.h>
16
17#include <fftw3.h>
18
19namespace Pscf {
20namespace Prdc {
21namespace Cpu {
22
23 using namespace Util;
24 using namespace Pscf;
25
36 template <int D>
37 class FFT
38 {
39
40 public:
41
45 FFT();
46
50 virtual ~FFT();
51
57 void setup(IntVec<D> const & meshDimensions);
58
59 // Real Data (Real <-> Complex Transforms)
60
75 void forwardTransform(RField<D> const & in, RFieldDft<D>& out) const;
76
94 void inverseTransformUnsafe(RFieldDft<D>& in, RField<D>& out) const;
95
108 void inverseTransformSafe(RFieldDft<D> const & in, RField<D>& out)
109 const;
110
111 // Complex Data (Complex <-> Complex Transforms)
112
131 void forwardTransform(CField<D> const & in, CField<D>& out) const;
132
146 void inverseTransform(CField<D> const & in, CField<D>& out) const;
147
148 // Accessors
149
153 IntVec<D> const & meshDimensions() const;
154
158 bool isSetup() const;
159
160 // Static function
161
173 static
174 void computeKMesh(IntVec<D> const & rMeshDimensions,
175 IntVec<D> & kMeshDimensions,
176 int & kSize );
177
195 static
196 bool hasImplicitInverse(IntVec<D> const & wavevector,
197 IntVec<D> const & meshDimensions);
198
199 private:
200
202 mutable RFieldDft<D> kFieldCopy_;
203
205 IntVec<D> meshDimensions_;
206
208 int rSize_;
209
211 int kSize_;
212
214 fftw_plan rcfPlan_;
215
217 fftw_plan criPlan_;
218
220 fftw_plan ccfPlan_;
221
223 fftw_plan cciPlan_;
224
226 bool isSetup_;
227
231 void makePlans(RField<D>& rField, RFieldDft<D>& kField,
232 CField<D>& cFieldIn, CField<D>& cFieldOut);
233
234 };
235
236 // Declarations of explicit specializations
237
238 template <>
239 void FFT<1>::makePlans(RField<1>& rField, RFieldDft<1>& kField,
240 CField<1>& cFieldIn, CField<1>& cFieldOut);
241
242 template <>
243 void FFT<2>::makePlans(RField<2>& rField, RFieldDft<2>& kField,
244 CField<2>& cFieldIn, CField<2>& cFieldOut);
245
246 template <>
247 void FFT<3>::makePlans(RField<3>& rField, RFieldDft<3>& kField,
248 CField<3>& cFieldIn, CField<3>& cFieldOut);
249
250 // Inline member functions
251
252 /*
253 * Has this object been setup?
254 */
255 template <int D>
256 inline bool FFT<D>::isSetup() const
257 { return isSetup_; }
258
259 /*
260 * Return the dimensions of the grid for which this was allocated.
261 */
262 template <int D>
263 inline IntVec<D> const & FFT<D>::meshDimensions() const
264 { return meshDimensions_; }
265
266 /*
267 * Does this wavevector have an implicit inverse?
268 */
269 template <int D>
270 inline
271 bool FFT<D>::hasImplicitInverse(IntVec<D> const & wavevector,
273 {
274 int i = wavevector[D-1];
275 int d = meshDimensions[D-1];
276 if ((i != 0) && (d - i > d/2 + 1)) {
277 return true;
278 } else {
279 return false;
280 }
281 }
282
283 #ifndef PRDC_CPU_FFT_TPP
284 // Suppress implicit instantiation
285 extern template class FFT<1>;
286 extern template class FFT<2>;
287 extern template class FFT<3>;
288 #endif
289
290} // namespace Pscf::Prdc::Cpu
291} // namespace Pscf::Prdc
292} // namespace Pscf
293#endif
An IntVec<D, T> is a D-component vector of elements of integer type T.
Definition IntVec.h:27
Field of complex double precision values on an FFT mesh.
Definition cpu/CField.h:30
Fourier transform wrapper.
Definition cpu/FFT.h:38
void inverseTransformUnsafe(RFieldDft< D > &in, RField< D > &out) const
Compute inverse (complex-to-real) DFT, overwriting the input.
Definition cpu/FFT.tpp:179
FFT()
Default constructor.
Definition cpu/FFT.tpp:57
void forwardTransform(RField< D > const &in, RFieldDft< D > &out) const
Compute forward (real-to-complex) discrete Fourier transform (DFT).
Definition cpu/FFT.tpp:151
static void computeKMesh(IntVec< D > const &rMeshDimensions, IntVec< D > &kMeshDimensions, int &kSize)
Compute dimensions and size of k-space mesh for DFT of real data.
Definition cpu/FFT.tpp:262
void inverseTransform(CField< D > const &in, CField< D > &out) const
Compute complex-to-complex inverse Fourier transform.
Definition cpu/FFT.tpp:241
bool isSetup() const
Has this FFT object been setup?
Definition cpu/FFT.h:256
static bool hasImplicitInverse(IntVec< D > const &wavevector, IntVec< D > const &meshDimensions)
Does this wavevector have implicit inverse in DFT or real data?
Definition cpu/FFT.h:271
void setup(IntVec< D > const &meshDimensions)
Setup grid dimensions, FFT plans and work space.
Definition cpu/FFT.tpp:92
IntVec< D > const & meshDimensions() const
Return the dimensions of the grid for which this was setup.
Definition cpu/FFT.h:263
virtual ~FFT()
Destructor.
Definition cpu/FFT.tpp:72
void inverseTransformSafe(RFieldDft< D > const &in, RField< D > &out) const
Compute inverse (complex-to-real) DFT without overwriting input.
Definition cpu/FFT.tpp:197
Fourier transform of a real field on an FFT mesh.
Field of real double precision values on an FFT mesh.
Definition cpu/RField.h:29
File containing preprocessor macros for error handling.
Fields and FFTs for periodic boundary conditions (CPU)
Definition CField.cpp:12
Periodic fields and crystallography.
Definition CField.cpp:11
PSCF package top-level namespace.
Definition param_pc.dox:1