I am using Python 3 for a task related to numerical analysis.
I have to plot some points originated from a sine function. Moreover, I need to do a cubic interpolation of these points (cubic spline).
So, these tasks are done. The output picture is great and the code works. However, I need to check if the the derivative of the cubic spline looks like a cosine function.
Take a look at this image:
In orange, you see the cosine function. In blue, you see the sine function. In red, the 5 dots that I sampled. In purple, you can see a linear interpolation. And, in dashes, you see the cubic interpolation.
I need to plot the derivative of the dashed curve and compare it to the orange one.
Intuitively, I know they are going to be pretty similar. However, I was not able to prove that with a graph.
That's the code:
import math
import random
from numpy import array
import numpy as np
import matplotlib.pyplot as plot
from scipy.interpolate import interp1d
from scipy import interpolate
from scipy.misc import derivative as deriv
def random_sine():
lista_f_x = []
lista_x = []
for i in range(1,6):
aleatorio = random.uniform(0,360)
aleatorio = math.radians(aleatorio)
lista_x.append(aleatorio)
sine_random = math.sin(aleatorio)
lista_f_x.append(sine_random)
lista_x = array(lista_x)
lista_f_x = array(lista_f_x)
return ("x",lista_x,"f(x)", lista_f_x)
# para ter um grupo controle melhor, deixe esses valores aleatórios, gerados uma vez, como fixos
fixed_x = array([5.80990031, 1.7836885, 4.62073799, 0.89337425, 5.62219906])
fixed_y = array([-0.45581264, 0.97742392, -0.99580299, 0.77919112, -0.61389568])
x = fixed_x
y = fixed_y
"""
caso deseje usar os valores fixos
basta inserir o comentário "#" nas linhas
39, 40 e 41 abaixo
"""
#teste_dinamico = random_sine()
#x = teste_dinamico[1]
#y = teste_dinamico[3]
time = np.arange(0,10,0.1)
amplitude = np.sin(time)
amplitude_cosine = np.cos(time)
plot.plot(time, amplitude, time, amplitude_cosine)
plot.title('Função Seno')
plot.xlabel('Coordenadas de X')
plot.ylabel('Seno(x)')
plot.grid(True, which='both')
plot.axhline(y=0, color='k')
pares_x_y = list(zip(x,y))
sort_pares_x_y = sorted(pares_x_y)
x_ordenado = []
y_ordenado_simetric = []
for i in sort_pares_x_y:
x_ordenado.append(i[0])
y_ordenado_simetric.append(i[1])
x_ordenado = array(x_ordenado)
y_ordenado_simetric = array(y_ordenado_simetric)
f = interp1d(x_ordenado, y_ordenado_simetric)
f2 = interp1d(x_ordenado, y_ordenado_simetric, kind="cubic")
plot.plot(x_ordenado, f2(x_ordenado))
minimo = min(x_ordenado)
maximo = max(x_ordenado)
xnew = np.linspace(minimo, maximo, num=400, endpoint=True)
plot.plot(x_ordenado, y_ordenado_simetric, 'o', xnew, f(xnew), '-', xnew, f2(xnew), '--')
plot.scatter(x,y)
plot.show()
I tried to follow this post. However, the post suggests a different package. I am using interp1d
so far and the post suggests using interpolate
. I tried converting what I did so far but it didn't work.
What can I do?
If I have a curve being plot with matplotlib, is there an easier way to plot the curve's derivative?
What's the best strategy to solve this?
1 - Should I try again and change everything to the other package suggested on SO?
2 - Should I use some numerical method for differentiation?
Thanks in advance.
Other packages or functions might of course be more handy, but for understanding, you may simply calculate the derivative (dy/dx) yourself and plot it.
plot.plot(xnew[:-1], np.diff(f2(xnew))/np.diff(xnew), color="red")
Adding this line will result in
where the red line is the derivative of f2
.