2015-10-01 8 views
6

Mi chiedo se esiste un modo semplice per decodificare un oggetto interp1d in scipy. L'approccio ingenuo non sembra funzionare.pickling scipy interp1d spline

import pickle 
import numpy as np 

from scipy.interpolate import interp1d 

x = np.linspace(0,1,10) 
y = np.random.rand(10) 

sp = interp1d(x, y) 

with open("test.pickle", "wb") as handle: 
    pickle.dump(sp, handle) 

Ciò solleva seguente PicklingError:

--------------------------------------------------------------------------- 
PicklingError        Traceback (most recent call last) 
<ipython-input-1-af4e3326e7d1> in <module>() 
    10 
    11 with open("test.pickle", "wb") as handle: 
---> 12  pickle.dump(sp, handle) 

PicklingError: Can't pickle <function interp1d._call_linear at 0x1058abf28>: attribute lookup _call_linear on scipy.interpolate.interpolate failed 

risposta

3

forse avvolgendolo in un'altra classe con __getstate__ e __setstate__ metodi:

from scipy.interpolate import interp1d 


class interp1d_picklable: 
    """ class wrapper for piecewise linear function 
    """ 
    def __init__(self, xi, yi, **kwargs): 
     self.xi = xi 
     self.yi = yi 
     self.args = kwargs 
     self.f = interp1d(xi, yi, **kwargs) 

    def __call__(self, xnew): 
     return self.f(xnew) 

    def __getstate__(self): 
     return self.xi, self.yi, self.args 

    def __setstate__(self, state): 
     self.f = interp1d(state[0], state[1], **state[2]) 
+0

sì, questo funzionerà. In effetti l'ho implementato in questo modo. – cel

+0

Questo fondamentalmente mette sottosopra gli array 'xi' e' yi' e gli eventuali keyargs. Quando si deseleziona, si chiama di nuovo 'interp1d' ... Se il tuo obiettivo è quello di risparmiare energia della CPU, questa non è una soluzione. – fheshwfq