2017-03-11 189 views
0

我有兩個輸入numpy數組,分別具有一組點的經度和緯度座標:latslonsNumpy:將函數應用於兩個numpy數組並返回兩個numpy數組

我繼承每個(lat,lon)對轉換爲(E,N)對的功能:

def convert(lat,lon): #takes two floats as arguments (unit: degrees) 
    ... 
    computation #Actual function is too long to post 
    ... 
    return N,E #returns two floats (unit: meters) 

我的問題:我怎麼能同時高效地應用相同的功能,兩個輸入numpy的陣列?

我想修改的功能,使得它返回一個列表:以這樣的方式

return [N,E] 

rows = int(lat.shape[0]) #lat and lon have the same shape 
cols = int(lat.shape[1]) 
easting=numpy.zeros(shape=(rows,cols)) 
northing=numpy.zeros(shape=(rows,cols)) 
for i in range(0, rows): 
    for j in range(0, cols): 
     northing=convert(lon[i][j])[0] #first element of the returned list 
     easting=convert(lat[i][j])[1] #second element of the returned list 

我還沒有測試過,但看着它我感覺不太舒服,這將起作用。任何見解將不勝感激。

+0

這將取決於'convert'功能的細節。它可能已經按照你想要的方式工作了,或者你可能不得不把它們切換成'np.sin',否則如果代碼依賴於你可以使用的API不能一次控制或替換一對元素。 – user2357112

回答

1

讓我們定義一個簡單的轉換

def convert(lat, lon): 
    return lat*np.pi/180, lon*np.pi/180 

frompyfunc是應用「標量」功能,以陣列的一個有用的方法;我們甚至可以把它拿在2個陣列,並返回2點陣列(一個元組)

In [233]: f = np.frompyfunc(convert,2,2) 
In [234]: lats=np.linspace(-45,45,5) 
In [235]: lons=np.linspace(0,100,5) 
In [236]: out = f(lats, lons) 
In [237]: out 
Out[237]: 
(array([-0.7853981633974483, -0.39269908169872414, 0.0, 0.39269908169872414, 
     0.7853981633974483], dtype=object), 
array([0.0, 0.4363323129985824, 0.8726646259971648, 1.3089969389957472, 
     1.7453292519943295], dtype=object)) 

的一個特點是,它返回一個對象數組,而你可能需要一個float數組:

In [238]: out[0].astype(float) 
Out[238]: array([-0.78539816, -0.39269908, 0.  , 0.39269908, 0.78539816]) 

或者與拆包:

In [239]: rlat, rlon = f(lats, lons) 
In [240]: rlat.astype(float) 
Out[240]: array([-0.78539816, -0.39269908, 0.  , 0.39269908, 0.78539816]) 

frompyfunc並通過輸入迭代。在其他測試中,它往往比更多顯式循環快兩倍。在這種情況下,因爲它返回一個元組,所以你不需要調用它兩次以獲得2個結果。

由於寫的,這convert作品同樣出色陣列與標量,從而

In [241]: convert(lats, lons) 
Out[241]: 
(array([-0.78539816, -0.39269908, 0.  , 0.39269908, 0.78539816]), 
array([ 0.  , 0.43633231, 0.87266463, 1.30899694, 1.74532925])) 

,這將是比Python的循環任何版本快得多。

因此,對於真正的速度,你想convert直接與數組工作。但是,如果它不能這樣做,那麼frompyfunc比自己動手循環稍微改進。

另一個優點frompyfunc - 它適用陣列廣播,如

f(lats[:,None], lons[None,:])