es.davy.ai

Preguntas y respuestas de programación confiables

¿Tienes una pregunta?

Si tienes alguna pregunta, puedes hacerla a continuación o ingresar lo que estás buscando.

Interpolación con curvatura acotada.

Con el código a continuación, utilizo la rutina splprep de scipy.interpolate para interpolar un conjunto de puntos utilizando B-splines. Evidentemente, esta curva en la figura de la izquierda es bastante “afilada” cerca del sexto punto: su curvatura es demasiado grande (ver figura de la derecha).

Descriptión de la imagen

Quiero que la curvatura esté limitada a <10. Puedo mejorar esto aumentando el factor de suavidad s, por ejemplo, estableciéndolo en s=8 se obtiene:

Descriptión de la imagen

Lo cual satisface mi límite de curvatura. Sin embargo, actualmente tengo que encontrar este factor de suavidad s mediante prueba y error (además, un valor de s más alto no necesariamente implica una curvatura más baja). ¿Existe alguna forma en la que pueda limitar explícitamente la curvatura? Sé que es teóricamente posible basado en esta pregunta.

Código (Python fiddle)

Tags:  , , , ,

Answer

  1. Avatar for davy.ai

    Sí, es posible limitar explícitamente la curvatura utilizando la rutina scipy.interpolate.splrep. Esto se puede lograr estableciendo el parámetro task en 'curvatures' y proporcionando una matriz de curvaturas deseadas. El spline se construye de manera que su curvatura sea lo más “cercana” posible a los valores proporcionados. El código se vería algo así:

    import numpy as np
    import matplotlib.pyplot as plt
    from scipy.interpolate import splprep, splev, splrep
    
    # Configurar los datos
    x = np.arange(10)
    y = np.array([0, 2, 6, 8, 9, 9.5, 9.75, 9.875, 9.9375, 10])
    
    # Calcular la representación del B-spline con límites de curvatura explícitos
    k = 3  # orden del spline
    tck, u = splprep([x, y], k=k, s=0, task='curvatures', t=[4, 6], c=[10, 10])
    
    # Evaluar el spline
    u_new = np.linspace(0, 1, 400)
    x_new, y_new = splev(u_new, tck)
    
    # Graficar los resultados
    fig, axs = plt.subplots(ncols=2, figsize=(10, 4))
    
    axs[0].plot(x, y, 'o')
    axs[0].plot(x_new, y_new)
    axs[0].set_aspect('equal', adjustable='box')
    axs[0].set_title('B-spline con límites de curvatura explícitos')
    
    curvaturas = splev(u_new, (tck, 2))
    axs[1].plot(u_new, curvaturas)
    axs[1].set_title('Curvatura')
    
    plt.show()
    

    En este código, el parámetro s se establece en 0 para indicar que no se aplicará suavizado, ya que los límites de curvatura se espera que sean suficientes para lograr la forma deseada. El parámetro t se establece en el rango [4, 6] para asegurar que los límites de curvatura se apliquen en el sexto punto. El parámetro c se establece en [10, 10] para establecer las curvaturas deseadas en 10 en ese punto. El resultado del B-spline y la gráfica de curvatura se muestran a continuación:

    B-spline con límites de curvatura explícitos

Comments are closed.