我已經開始在cython中使用memoryviews來訪問numpy數組。他們具有的各種優點之一是它們比舊的numpy緩衝區支持要快得多: http://docs.cython.org/src/userguide/memoryviews.html#comparison-to-the-old-buffer-supportcython memoryview比預期慢
但是,我有一個例子,其中舊的numpy緩衝區支持比memoryviews更快! 這怎麼可能?我想知道我是否正確使用了記憶體?
這是我的測試:
import numpy as np
cimport numpy as np
cimport cython
@cython.boundscheck(False)
@cython.wraparound(False)
cpdef np.ndarray[np.uint8_t, ndim=2] image_box1(np.ndarray[np.uint8_t, ndim=2] im,
np.ndarray[np.float64_t, ndim=1] pd,
int box_half_size):
cdef unsigned int p0 = <int>(pd[0] + 0.5)
cdef unsigned int p1 = <int>(pd[1] + 0.5)
cdef unsigned int top = p1 - box_half_size
cdef unsigned int left = p0 - box_half_size
cdef unsigned int bottom = p1 + box_half_size
cdef unsigned int right = p0 + box_half_size
cdef np.ndarray[np.uint8_t, ndim=2] box = im[top:bottom, left:right]
return box
@cython.boundscheck(False)
@cython.wraparound(False)
cpdef np.uint8_t[:, ::1] image_box2(np.uint8_t[:, ::1] im,
np.float64_t[:] pd,
int box_half_size):
cdef unsigned int p0 = <int>(pd[0] + 0.5)
cdef unsigned int p1 = <int>(pd[1] + 0.5)
cdef unsigned int top = p1 - box_half_size
cdef unsigned int left = p0 - box_half_size
cdef unsigned int bottom = p1 + box_half_size
cdef unsigned int right = p0 + box_half_size
cdef np.uint8_t[:, ::1] box = im[top:bottom, left:right]
return box
時機結果是:
image_box1:輸入numpy的: 100000循環,最好的3:11.2%環我們
image_box2:memoryview: 100000循環,最好的3:每循環18.1美元
這些測量是從IPython使用%timeit完成image_bo x1(im,pd,box_half_size)
我猜你是從python計時這些功能?從那時起,返回值就是第二個函數中的'np.ndarray'(我假設),這可能已經解釋了減速,因爲使得'np.ndarray'有點額外的工作,這裏沒有太多的工作要做總體。 – seberg
是的,我從IPython使用以下命令對它們進行了計時: %timeit image_box1(im,pd,box_half_size) 我剛剛編輯了我的問題以包含cython內的時間。記憶體觀點仍然較慢! – martinako
更正!你是對的,延遲是從numpy數組轉換到memoryview! – martinako