[問題] python 速度 FOR_LOOP

作者: redonizuka (R大)   2014-08-05 00:27:35
目前剛接觸python
以python撰寫了一段Sobel影像處理,程式碼如下
===================================================
import cv2
import numpy as np
img=cv2.imread("/home/chenposhao/Desktop/IMAGE/cameraman.tif",0)
[row,col]=img.shape
resx=np.zeros((row,col),np.uint8)
kernalx=np.array([[1,2,1],[0,0,0],[-1,-2,-1]])
kernaly=np.array([[1,0,-1],[2,0,-2],[1,0,-1]])
for x in range(row):
for y in range(col):
if x==0 or x==row-1 or y==0 or y==col-1:
pass
else:
subxsum=0
subysum=0
for i in range(-1,2):
for j in range(-1,2):
newx=img[x+i,y+j]*kernalx[i+1,j+1]
subxsum=subxsum+newx
newy=img[x+i,y+j]*kernaly[i+1,j+1]
subysum=subysum+newy
respixel=abs(subxsum+subysum/2)
if respixel>255:
respixel=255
elif respixel<0:
respixel=0
resx[x,y]=respixel
cv2.imshow("IMAGE",img)
cv2.imshow("SOBELX",resx)
cv2.waitKey(0)
cv2.destroyAllWindows()
================================================================
首先要先說,跑的圖片是256*256
我知道CV有SOBEL函式庫可以用,
但因為用他的函式庫發現他並沒有將所計算的像素取絕對值
因此有方向性的問題,為了驗證才寫此程式碼
但發現這個程式碼再執行的時候不如預期的快
從中間的for x in range(row): 到 resx[x,y]=respixel
整個FORLOOP跑完要5.5秒左右
VB,C幾毫秒即可跑完
想問一下這是python所必須要克服的事情嘛?
因為剛接觸Python,早有相傳他因為直譯所以速度慢
但想不到落差有些許的大
還是說其實這是能改善的?
謝謝
作者: grtfor (哦啦啦)   2014-08-05 01:00:00
直譯擅長的不在效率呀,有改進方法但要追上很難~
作者: ccwang002 (亮)   2014-08-05 01:10:00
你不應該一個元素一個元素自己乘,這樣會慢很多多用 numpy array級操作才會快,python for-loop 會太慢另外,我找到 scipy.ndimage.filters.sobel 可以呼叫點旁邊的 source 就可以知道它 code 怎麼寫的
作者: vic0330 (Shanho)   2014-08-05 08:37:00
不知道range改xrange會不會比較快
作者: redonizuka (R大)   2014-08-05 09:36:00
想更詳細的問一下何謂 numpy array級操作
作者: ccwang002 (亮)   2014-08-05 10:24:00
比如 i j 迴圈改成 np.sum(img * (kernalx + kernaly))選部份矩陣應該用 img[x:x+3, y:y+3] 這型式的取值大原則避免自己寫 for 或複雜運算,numpy 本身是 C 速度看 scipy 寫法,它只用了 correlate1d 這函式就實作完了我不懂 sobel 沒法給建議,不夠快的話也可考慮 Cython
作者: LiloHuang (十年一刻)   2014-08-06 20:27:00
它會編譯成 bytecode 來跑呀,只是 CPython 挺慢是事實現階段 CPython 也沒有像 Java 或 .NET 有做 JIT 優化迴圈自然就是不會快去哪邊,做 Convolution 用 GPU 最快退而求其次就是用 numpy.convolve + numpy.absoluteNumbaPro 聽說挺不錯的,可以用到 GPU 來加速...另外,Sobel filter 是 separable filter 我想你知道 :D儘管從 2D kernel 改 1D kernel 對於 Python 也沒快很多這個 http://goo.gl/CrQiXl 可以跑跑看,也許有幫助 :P
作者: fischcheng (布阿送)   2014-08-08 06:36:00
Numba
作者: LiloHuang (十年一刻)   2014-08-08 09:28:00
社群版的 Numba 效果應該也不錯吧,NumbaPro 得花錢就是
作者: ming1053 (ming)   2014-08-11 11:10:00
跟matlab道理差不多啊 多用 vectorization
作者: redonizuka (R大)   2014-08-13 16:31:00
感謝大家的發問,我持續摸索,大家對我幫助很大,謝謝
作者: neutrino (十年一夢)   2014-08-14 16:45:00
similar question in stackoverflow http://ppt.cc/pSIw

Links booklink

Contact Us: admin [ a t ] ucptt.com