2012-12-18 32 views
5

Cố gắng sử dụng gấu trúc cực kỳ hữu ích để xử lý dữ liệu theo chuỗi thời gian, hiện tại tôi đang vấp phải sự thật là dường như không tồn tại các thư viện có thể trực tiếp nội suy (với đường spline hoặc tương tự) trên dữ liệu có DateTime trục x? Tôi dường như luôn bị buộc phải chuyển đổi đầu tiên thành một số số dấu phẩy động, như số giây từ năm 1980 hoặc một cái gì đó tương tự.Splines của Python hoặc các nội suy khác hoạt động theo thời gian trên trục x?

Tôi đã cố gắng những điều sau đây cho đến nay, xin lỗi cho các định dạng lạ, tôi có công cụ này chỉ trong máy tính xách tay ipython, và tôi không thể sao chép tế bào từ đó:

from scipy.interpolate import InterpolatedUnivariateSpline as IUS 
type(bb2temp): pandas.core.series.TimeSeries 
s = IUS(bb2temp.index.to_pydatetime(), bb2temp, k=1) 
--------------------------------------------------------------------------- 
TypeError         Traceback (most recent call last) 
<ipython-input-67-19c6b8883073> in <module>() 
----> 1 s = IUS(bb2temp.index.to_pydatetime(), bb2temp, k=1) 

/Library/Frameworks/EPD64.framework/Versions/7.3/lib/python2.7/site-packages/scipy/interpolate/fitpack2.py in __init__(self, x, y, w, bbox, k) 
    335   #_data == x,y,w,xb,xe,k,s,n,t,c,fp,fpint,nrdata,ier 
    336   self._data = dfitpack.fpcurf0(x,y,k,w=w, 
--> 337          xb=bbox[0],xe=bbox[1],s=0) 
    338   self._reset_class() 
    339 

TypeError: float() argument must be a string or a number 

Bằng cách sử dụng bb2temp.index.values (mà trông như thế này:

array([1970-01-15 184:00:35.884999, 1970-01-15 184:00:58.668999, 
     1970-01-15 184:01:22.989999, 1970-01-15 184:01:45.774000, 
     1970-01-15 184:02:10.095000, 1970-01-15 184:02:32.878999, 
     1970-01-15 184:02:57.200000, 1970-01-15 184:03:19.984000, 

) như x-luận, thú vị, lớp Spline không tạo ra một người xen vào, nhưng nó vẫn phá vỡ khi cố gắng suy/ngoại suy đến một DateTimeIndex lớn hơn (đó là mục tiêu cuối cùng của tôi ở đây) . Dưới đây là làm thế nào mà trông:

all_times = divcal.timed.index.levels[2] # part of a MultiIndex 

all_times 
<class 'pandas.tseries.index.DatetimeIndex'> 
[2009-07-20 00:00:00.045000, ..., 2009-07-20 00:30:00.018000] 
Length: 14063, Freq: None, Timezone: None 

s(all_times.values) # applying the above generated interpolator 
--------------------------------------------------------------------------- 
TypeError         Traceback (most recent call last) 
<ipython-input-74-ff11f6d6d7da> in <module>() 
----> 1 s(tall.values) 

/Library/Frameworks/EPD64.framework/Versions/7.3/lib/python2.7/site-packages/scipy/interpolate/fitpack2.py in __call__(self, x, nu) 
    219 #   return dfitpack.splev(*(self._eval_args+(x,))) 
    220 #  return dfitpack.splder(nu=nu,*(self._eval_args+(x,))) 
--> 221   return fitpack.splev(x, self._eval_args, der=nu) 
    222 
    223  def get_knots(self): 

/Library/Frameworks/EPD64.framework/Versions/7.3/lib/python2.7/site-packages/scipy/interpolate/fitpack.py in splev(x, tck, der, ext) 
    546 
    547   x = myasarray(x) 
--> 548   y, ier =_fitpack._spl_(x, der, t, c, k, ext) 
    549   if ier == 10: 
    550    raise ValueError("Invalid input data") 

TypeError: array cannot be safely cast to required type 

Tôi cố gắng để sử dụng s(all_times)s(all_times.to_pydatetime()) là tốt, với cùng TypeError: array cannot be safely cast to required type.

Tôi có, thật đáng buồn, đúng không? Mọi người có quen với việc chuyển đổi thời gian thành các điểm trôi nổi quá nhiều đến mức không ai nghĩ rằng các ý tưởng này sẽ hoạt động tự động tốt? (Cuối cùng tôi cũng đã tìm thấy một dự án siêu hữu ích để đóng góp ..) Hay bạn muốn chứng minh cho tôi sai và kiếm được một số điểm SO? ;)

Chỉnh sửa: Cảnh báo: Kiểm tra dữ liệu gấu trúc của bạn cho NaN trước khi bạn giao cho các thói quen nội suy. Họ sẽ không phàn nàn về bất cứ điều gì nhưng chỉ im lặng thất bại.

Trả lời

5

Vấn đề là những thói quen fitpack được sử dụng bên dưới yêu cầu phao nổi. Vì vậy, tại một số điểm có phải là một chuyển đổi từ datetime để nổi. Chuyển đổi này rất dễ dàng. Nếu bb2temp.index.values là mảng datetime của bạn, chỉ cần làm:

In [1]: bb2temp.index.values.astype('d') 
Out[1]: 
array([ 1.22403588e+12, 1.22405867e+12, 1.22408299e+12, 
     1.22410577e+12, 1.22413010e+12, 1.22415288e+12, 
     1.22417720e+12, 1.22419998e+12]) 

Bạn chỉ cần phải vượt qua đó để đường Spline. Và để chuyển đổi kết quả trở lại đối tượng datetime, bạn thực hiện results.astype('datetime64').

+0

Tôi đã nghĩ nó phải dễ dàng, cảm ơn! Nhưng tôi có giả định rằng một bản vá cho các thói quen nội suy scipy cấp cao chỉ có thể làm điều đó cho tôi? –

+0

Chắc chắn, một bản vá sẽ làm điều đó. Nhưng dường như vẫn còn quá mức với tôi. Nó có thể là một cái gì đó đơn giản như 'nếu array.dtype == 'datetime64': array = array.astype ('d')', và sau đó ngược lại cho đầu ra. – tiago

+0

đó là lý do tại sao tôi đang bối rối rằng họ không làm điều đó anyway ..;) Tại sao giới thiệu các lớp học cấp cao trên đầu trang của fitpack nếu họ không làm việc cho bạn? Nhiều bước giữa splrep và InterpolatedUnivariateSpline có thể đơn giản là một hoặc hai lớp lót. Trong tổng số, họ đếm. –

Các vấn đề liên quan