Im attempting to recreate a fourier approximation for a python function with a given numerical output (without using external libraries), however my function only works in the range of numbers from 0.0 to 1.0. Ive considered simply multiplying any given input larger than 1.0 to a negative power of ten, and then multiplying by the positive power once the result has been held.
However, as I am limiting myself to not use external libraries (ie something like Decimal
or mpmath
), I feel as though this solution would not work well given python's limited floating-point precision. I feel as though there's a much less 'hacky' solution to this problem, however I am unable to figure out what such may be.
e = 2.718281828459045
i_tau = 6.283185307179586j
def integrate(func, a, b, step=0.001):
total = 0
while a <= b:
a += step
total += func(a)*step
return total
def fourier_constant(func, n):
return integrate(lambda x: func(x)*e**(-n*i_tau*x), 0, 1)
def fourier_approx(func, count):
return lambda x: sum([fourier_constant(func, n)*e**(n*i_tau*x) for n in range(-count, count+1)]).real
series_accuracy = 500
test_value = 0.3 # FIX: only works in range 0.0-1.0
function_to_approximate = lambda x: x*2
approximated_function = fourier_approx(function_to_approximate, series_accuracy)
print(f"expected output at value {test_value} : {function_to_approximate(test_value)}")
print(f" actual output at value {test_value} : {approximated_function(test_value)}")
This code is computing a nice triangular wave (which is in no way restricted to the interval [0, 1]). I limited the number of terms to 5 then to 50 to make the Runge phenomenon clearly visible.
By the way, the computation is perfectly accurate.