2 votes

Problème d'interpolation de spline univariée lié aux données avec SCIPY

J'ai un problème étrange en essayant d'interpoler des données en utilisant la fonction UnivariateSpline. Interpoler à travers tous les points (s=0) et la fonction spline ne donne pas de résultat sur l'ensemble des données. Le résultat pour s>=1 est aussi très étrange. Comme je pense que cela est lié aux données que j'utilise, je les joins en pièce jointe.
Je suis bloqué, donc si quelqu'un a une bonne idée pour une solution, je vous serais vraiment reconnaissant.

Merci,

voici une partie du code:

import numpy as np
import matplotlib.pyplot as plt
from scipy.interpolate import UnivariateSpline

def openfile(infilename):
    ifile = open(infilename, 'r') # ouvrir le fichier en lecture
    lines = ifile.readlines()
    ifile.close()
    return lines

def extractData(lines):
    data=[]
    CV=[]

    for i in range(len(lines)):
        item=lines[i].split()
        for j in range(len(item)):
            item[j]=float(item[j])
            data.append(item[j])

    CV=np.array(data)
    CV.shape = (len(CV)/3,3)
    return CV

if __name__ == "__main__":

    lines=openfile("D:\capamos\LOCOS\cap15L1_rec_mod.csv")
    CV=extractData(lines)
    Vg1=CV[:,0]
    C1=CV[:,1]
    Cmax=C1.max()
    Cmin=C1.min()
    S=0.002
    Cfb=compute(Cmax,Cmin,S) #calculer la capacitance en bande plate
    print "Cfb=",Cfb

    splineCV= UnivariateSpline(Vg1,C1,s=0)
    x = linspace(-5, 5, 1000)   # juste pour dessiner la fonction spline
    y=splineCV(x)
    Vfb=splineCV(Cfb)  # trouver la tension de bande plate à Cfb
    print "Vfb=",Vfb
    print y

    plt.figure(1)
    p1=plot(Vg1,C1,'b',label='edge')
    p2=plot(x,y,'g')
    plt.axis([-6,6,1e-11,80e-12])

Et voici les données:

5   6.35E-011   -4.79E-010
4.95    6.35E-011   -1.91E-010
4.9 6.35E-011   -2.19E-010
4.85    6.35E-011   -4.57E-010
4.8 6.35E-011   -1.24E-010
4.75    6.35E-011   -3.50E-010
4.7 6.35E-011   -4.15E-010
4.65    6.34E-011   2.37E-010
4.6 6.35E-011   -2.84E-010
4.55    6.34E-011   -2.18E-010
4.5 6.35E-011   1.90E-010
4.45    6.34E-011   -7.71E-011
4.4 6.34E-011   -6.89E-010
4.35    6.34E-011   -2.79E-010
4.3 6.33E-011   -3.37E-010
4.25    6.33E-011   -4.32E-010
4.2 6.33E-011   -7.29E-010
4.15    6.33E-011   -2.17E-012
4.1 6.33E-011   1.62E-010
4.05    6.32E-011   -1.63E-010
4   6.32E-011   -2.73E-010
3.95    6.33E-011   -9.93E-011
3.9 6.32E-011   1.77E-010
3.85    6.32E-011   -3.26E-010
3.8 6.32E-011   -2.47E-010 
3.75    6.32E-011   -1.59E-010
3.7 6.30E-011   -1.03E-010
3.65    6.30E-011   -7.15E-011
3.6 6.31E-011   -3.02E-010
3.55    6.30E-011   2.52E-010
3.5 6.31E-011   -2.98E-010
3.45    6.29E-011   -1.21E-010
3.4 6.29E-011   -1.97E-010
3.35    6.29E-011   -6.97E-011
3.3 6.29E-011   -1.68E-010
3.25    6.28E-011   2.52E-010
3.2 6.28E-011   -2.66E-010
3.15    6.28E-011   -6.52E-010
3.1 6.27E-011   2.78E-011
3.05    6.27E-011   -4.69E-010
3   6.27E-011   -2.63E-010
2.95    6.26E-011   -3.00E-010
2.9 6.26E-011   -2.23E-010
2.85    6.25E-011   -4.05E-010
2.8 6.25E-011   -2.68E-010
2.75    6.25E-011   -5.19E-010
2.7 6.23E-011   9.14E-011
2.65    6.24E-011   -5.05E-010
2.6 6.22E-011   -4.39E-010
2.55    6.21E-011   -4.11E-010
2.5 6.21E-011   1.71E-010
2.45    6.20E-011   2.35E-010
2.4 6.19E-011   -1.20E-010
2.35    6.18E-011   -9.91E-012
2.3 6.18E-011   -6.99E-011
2.25    6.17E-011   -2.35E-010
2.2 6.15E-011   -6.35E-010
2.15    6.14E-011   -2.10E-010
2.1 6.13E-011   -3.70E-010
2.05    6.11E-011   -2.89E-010
2   6.10E-011   1.06E-010
1.95    6.09E-011   -3.23E-010
1.9 6.07E-011   1.37E-010
1.85    6.05E-011   -2.40E-010
1.8 6.03E-011   -1.04E-010
1.75    6.00E-011   -1.72E-010
1.7 5.98E-011   -4.59E-011
1.65    5.96E-011   -4.71E-010
1.6 5.91E-011   -4.40E-010
1.55    5.88E-011   -2.11E-010
1.5 5.84E-011   -3.97E-010
1.45    5.78E-011   -1.37E-010
1.4 5.74E-011   -2.56E-010
1.35    5.66E-011   -3.33E-010  
1.3 5.58E-011   -1.61E-011
1.25    5.50E-011   -3.73E-011
1.2 5.39E-011   -2.02E-010 
1.15    5.27E-011   2.62E-011
1.1 5.12E-011   1.48E-010
1.05    4.94E-011   -5.94E-011 
1   4.75E-011   -2.22E-010
0.95    4.52E-011   5.05E-011
0.9 4.27E-011   -2.08E-010
0.85    4.02E-011   -3.30E-011
0.8 3.77E-011   2.84E-010
0.75    3.52E-011   -2.50E-010
0.7 3.30E-011   7.79E-010
0.65    3.11E-011   9.33E-010
0.6 2.93E-011   9.51E-010
0.55    2.78E-011   7.86E-010
0.5 2.65E-011   5.22E-010
0.45    2.54E-011   7.77E-011
0.4 2.44E-011   7.67E-011
0.35    2.36E-011   -2.22E-010
0.3 2.28E-011   -1.93E-010
0.25    2.21E-011   -1.78E-010
0.2 2.15E-011   4.91E-011
0.15    2.09E-011   -1.97E-010
0.1 2.04E-011   -4.07E-010
0.05    1.99E-011   -1.37E-0 10
0   1.95E-011   -1.58E-010
-0.05   1.91E-011   -2.27E-010
-0.1    1.88E-011   -4.24E-010
-0.15   1.86E-011   -3.00E-010
-0.2    1.83E-011   2.35E-010
-0.25   1.81E-011   2.87E-010
-0.3    1.79E-011   -7.89E-011
-0.35   1.78E-011   5.05E-010
-0.4    1.77E-011   8.43E-011
-0.45   1.76E-011   -1.67E-010
-0.5    1.75E-011   -3.21E-010
-0.55   1.74E-011   -1.39E-010
-0.6    1.74E-011   -2.56E-010
-0.65   1.73E-011   6.28E-011
-0.7    1.72E-011   -1.39E-010
-0.75   1.71E-011   1.07E-010
-0.8    1.70E-011   2.98E-010
-0.85   1.69E-011   -4.11E-011
-0.9    1.68E-011   -2.59E-010
-0.95   1.68E-011   -4.53E-010 
-1  1.67E-011   -4.97E-010
-1.05   1.66E-011   -3.11E-010
-1.1    1.65E-011   1.02E-010
-1.15   1.64E-011   3.58E-010
-1.2    1.64E-011   2.33E-011
-1.25   1.63E-011   -1.96E-011
-1.3    1.62E-011   -2.55E-010
-1.35   1.61E-011   -1.24E-010
-1.4    1.60E-011   9.76E-011
-1.45   1.60E-011   -1.30E-010
-1.5    1.59E-011   -1.94E-010
-1.55   1.59E-011   3.96E-010
-1.6    1.58E-011   -9.73E-013
-1.65   1.58E-011   -3.42E-011
-1.7    1.56E-011   2.40E-010
-1.75   1.56E-011   -2.59E-010
-1.8    1.55E-011   -2.25E-010
-1.85   1.55E-011   -2.09E-010
-1.9    1.54E-011   6.10E-011
-1.95   1.54E-011   -1.91E-010  
-2  1.53E-011   -5.28E-011
-2.05   1.52E-011   -1.15E-010
-2.1    1.52E-011   -1.54E-010
-2.15   1.51E-011   -9.81E-011
-2.2    1.51E-011   -2.18E-011
-2.25   1.50E-011   -4.79E-011
-2.3    1.50E-011   4.71E-011
-2.35   1.50E-011   -3.73E-010
-2.4    1.49E-011   1.50E-010
-2.45   1.48E-011   1.08E-010
-2.5    1.48E-011   -1.51E-010
-2.55   1.48E-011   1.72E-010
-2.6    1.47E-011   -3.49E-011
-2.65   1.47E-011   -2.53E-010
-2.7    1.46E-011   -1.64E-010  
-2.75   1.46E-011   -2.40E-011
-2.8    1.45E-011   -7.15E-011
-2.85   1.45E-011   -2.91E-010
-2.9    1.45E-011   6.30E-011
-2.95   1.45E-011   -2.76E-010
-3  1.45E-011   2.01E-010
-3.05   1.44E-011   -2.15E-010
-3.1    1.44E-011   -9.85E-011  
-3.15   1.43E-011   2.53E-011
-3.2    1.44E-011   5.78E-012
-3.25   1.43E-011   -3.54E-010
-3.3    1.43E-011   3.60E-011
-3.35   1.44E-011   -1.14E-010
-3.4    1.44E-011   -2.33E-010
-3.45   1.44E-011   -3.83E-010 
-3.5    1.44E-011   -3.10E-010
-3.55   1.43E-011   -9.04E-011
-3.6    1

5voto

Joe Kington Points 68089

Votre problème est que vos coordonnées x d'entrée sont dans un ordre décroissant. UnivariateSpline attend qu'elles soient dans un ordre croissant.

Voici une version plus compacte de votre code ci-dessus qui reproduit les problèmes que vous rencontriez. (Les données que vous aviez dans votre question sont censées être dans un fichier appelé data.txt).

import numpy as np
import matplotlib.pyplot as plt
from scipy.interpolate import UnivariateSpline

data = np.loadtxt('data.txt')
x = data[:,0]
y = data[:,1]

spline = UnivariateSpline(x, y, s=0)
xi = np.linspace(x.min(), x.max(), 1000)
yi = spline(xi) 

p1 = plt.plot(x, y, 'bo', label='Points Originaux')
p2 = plt.plot(xi, yi, 'g', label='Points Interpolés')
plt.legend()
plt.show()

description de l'image

Évidemment, cela n'a pas fonctionné correctement.

Cependant, si vous regardez vos données d'entrée, vos coordonnées "x" sont dans un ordre décroissant. Si nous inverssons simplement les données d'entrée "x" et "y", cela fonctionne parfaitement.

import numpy as np
import matplotlib.pyplot as plt
from scipy.interpolate import UnivariateSpline

data = np.loadtxt('data.txt')
x = data[:,0][::-1] # Inversion des données d'entrée...
y = data[:,1][::-1]

spline = UnivariateSpline(x, y, s=0)
xi = np.linspace(x.min(), x.max(), 1000)
yi = spline(xi) 

p1 = plt.plot(x, y, 'bo', label='Points Originaux')
p2 = plt.plot(xi, yi, 'g', label='Points Interpolés')
plt.legend()
plt.show()

description de l'image

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X