/// <summary> /// Initializes a new instance of the Fourier transformer with the given sign and normalization conventions. /// </summary> /// <param name="size">The series length of the transformer, which must be positive.</param> /// <param name="signConvention">The sign convention of the transformer.</param> /// <param name="normalizationConvention">The normalization convention of the transformer.</param> public Fourier(int size, FourierSign signConvention, FourierNormalization normalizationConvention) { if (size < 1) throw new YAMPArgumentRangeException("size", 0); this.size = size; this.signConvention = signConvention; this.normalizationConvention = normalizationConvention; // pre-compute the Nth complex roots of unity this.roots = Helpers.ComputeRoots(size, +1); // decompose the size into prime factors this.factors = Factors(size); // store a plan for the transform based on the prime factorization plan = new List<Transformlet>(); foreach (Factor factor in factors) { Transformlet t; switch (factor.Value) { // use a radix-specialized transformlet when available case 2: t = new RadixTwoTransformlet(size, roots); break; case 3: t = new RadixThreeTransformlet(size, roots); break; // eventually, we should make an optimized radix-4 transform case 5: t = new RadixFiveTransformlet(size, roots); break; case 7: t = new RadixSevenTransformlet(size, roots); break; case 11: case 13: // the base transformlet is R^2, but when R is small, this can still be faster than the Bluestein algorithm // timing measurements appear to indicate that this is the case for radix 11 and 13 // eventually, we should make optimized Winograd transformlets for these factors t = new Transformlet(factor.Value, size, roots); break; default: // for large factors with no available specialized transformlet, use the Bluestein algorithm t = new BluesteinTransformlet(factor.Value, size, roots); break; } t.Multiplicity = factor.Multiplicity; plan.Add(t); } }
/// <summary> /// Initializes a new instance of the Fourier transformer with the given sign and normalization conventions. /// </summary> /// <param name="size">The series length of the transformer, which must be positive.</param> /// <param name="signConvention">The sign convention of the transformer.</param> /// <param name="normalizationConvention">The normalization convention of the transformer.</param> public Fourier(int size, FourierSign signConvention, FourierNormalization normalizationConvention) { if (size < 1) { throw new YAMPArgumentRangeException("size", 0); } this.size = size; this.signConvention = signConvention; this.normalizationConvention = normalizationConvention; // pre-compute the Nth complex roots of unity this.roots = Helpers.ComputeRoots(size, +1); // decompose the size into prime factors this.factors = Factors(size); // store a plan for the transform based on the prime factorization plan = new List <Transformlet>(); foreach (Factor factor in factors) { Transformlet t; switch (factor.Value) { // use a radix-specialized transformlet when available case 2: t = new RadixTwoTransformlet(size, roots); break; case 3: t = new RadixThreeTransformlet(size, roots); break; // eventually, we should make an optimized radix-4 transform case 5: t = new RadixFiveTransformlet(size, roots); break; case 7: t = new RadixSevenTransformlet(size, roots); break; case 11: case 13: // the base transformlet is R^2, but when R is small, this can still be faster than the Bluestein algorithm // timing measurements appear to indicate that this is the case for radix 11 and 13 // eventually, we should make optimized Winograd transformlets for these factors t = new Transformlet(factor.Value, size, roots); break; default: // for large factors with no available specialized transformlet, use the Bluestein algorithm t = new BluesteinTransformlet(factor.Value, size, roots); break; } t.Multiplicity = factor.Multiplicity; plan.Add(t); } }