OpenCV-Python
說明使用 Python 和 OpenCV 來實作影像的前處理和基本功能。
1. 載入圖檔並顯示
import cv2 as cv
img = [Link]("[Link]") #讀取圖片
[Link]("img", img) #顯示圖片
[Link](0) #等待按鍵被觸發後繼續
[Link]() #關閉所有顯示圖片的視窗
[Link] 讀進來的資料,會儲存成一個 Numpy 的陣列。此陣列的前兩個維度
分別是圖片的高度和寬度,第三個維度則是 channel(RGB 彩色圖片的 channel
是 3,灰階圖片則是 1)。
2. 色彩空間的轉換
import cv2 as cv
img = [Link]("[Link]") #讀取圖片
gray = [Link](img, cv.COLOR_BGR2GRAY) #RGB 轉灰階
hsv = [Link](img, cv.COLOR_BGR2HSV) #RGB 轉 HSV
bgr = [Link](img, cv.COLOR_HSV2BGR) #HSV 轉 RGB
[Link]("Gray_img", gray) #顯示圖片
[Link]("HSV_img", hsv) #顯示圖片
[Link]("BGR_img", bgr) #顯示圖片
[Link](0) #等待按鍵被觸發後繼續
[Link]() #關閉所有顯示圖片的視窗
3. 二值化
import cv2 as cv
img = [Link]("[Link]") #讀取圖片
gray = [Link](img, cv.COLOR_BGR2GRAY) #RGB 轉灰階
_, binary = [Link](gray, 128, 255, cv.THRESH_BINARY) #二值
化
[Link]("img", img) #顯示圖片
[Link](0) #等待按鍵被觸發後繼續
[Link]() #關閉所有顯示圖片的視窗
[Link] 將圖片從灰階轉成黑白,會有兩個回傳值
4. 另一種二值化
在 HSV 空間裡,根據區間(lower/upper)分割。以 HSV 紫色區間為例。
import cv2 as cv
import numpy as np
img = [Link]("[Link]") #讀取圖片
hsv = [Link](img, cv.COLOR_BGR2HSV) #RGB 轉灰階
lower = [Link]([141, 0, 0]) #hsv 紫色下限
upper = [Link]([164, 145, 197]) #hsv 紫色上限
binary = [Link](hsv, lower, upper) #取出紫色區間的範圍
[Link]("binary", binary) #顯示圖片
[Link](0) #等待按鍵被觸發後繼續
[Link]() #關閉所有顯示圖片的視窗
5. 位元運算處理(Bitwise)
import cv2 as cv
import numpy as np
img = [Link]("[Link]") #讀取圖片
hsv = [Link](img, cv.COLOR_BGR2HSV) #RGB 轉灰階
lower = [Link]([141, 0, 0]) #hsv 紫色下限
upper = [Link]([164, 145, 197]) #hsv 紫色上限
binary = [Link](hsv, lower, upper) #取出紫色區間的範圍
[Link]("binary", binary)
mask = cv.bitwise_not(binary) #將 binary 反向的結果
[Link]("binary_inv", mask) #顯示圖片
bitwise_not = cv.bitwise_not(img, mask=binary)#將原圖和 binary 做
not
[Link]("bitwise_not", bitwise_not) #顯示圖片
bitwise_and = cv.bitwise_and(img, img, mask=binary)#將原圖和 binary
做 and
[Link]("bitwise_and", bitwise_and) #顯示圖片
bitwise_or = cv.bitwise_or(img, img, mask=mask)#將原圖和 mask 做
or
[Link]("bitwise_or", bitwise_or) #顯示圖片
[Link](0) #等待按鍵被觸發後繼續
[Link]() #關閉所有顯示圖片的視窗
6. 仿射變換(Affine Transformation)
import cv2 as cv
import numpy as np
img = [Link]("[Link]") #讀取圖片
rows, cols = [Link][:2] #圖片的長、寬
M = np.float32([[1, 0, 100], [0, 1, 50]]) #仿射矩陣
translation = [Link](img, M, (cols, rows)) #將原圖位移到(100,
50)的位置
[Link]("Translation", translation) #顯示圖片
[Link](0) #等待按鍵被觸發後繼續
[Link]() #關閉所有顯示圖片的視窗
7. 旋轉
import cv2 as cv
img = [Link]("[Link]") #讀取圖片
rows, cols = [Link][:2] #圖片的長、寬
M = cv.getRotationMatrix2D((cols/2, rows/2), 45, 1) #得到旋轉矩
陣
rotation = [Link](img, M, (cols, rows)) #將原圖旋轉
[Link]("Rotation", rotation) #顯示圖片
[Link](0) #等待按鍵被觸發後繼續
[Link]() #關閉所有顯示圖片的視窗
8. 縮放
import cv2 as cv
img = [Link]("[Link]") #讀取圖片
rows, cols = [Link][:2] #圖片的長、寬
resize = [Link](img, (cols*2, rows*2),
interpolation=cv.INTER_CUBIC) #將原圖放大兩倍
[Link]("Resize", resize) #顯示圖片
[Link](0) #等待按鍵被觸發後繼續
[Link]() #關閉所有顯示圖片的視窗
注意:[Link] 的 dsize 參數不可有小數點。
9. 裁切
import cv2 as cv
img = [Link]("[Link]") #讀取圖片
ROI = img[100:300, 80:250] #用 numpy 自行切割
[Link]("ROI", ROI) #顯示圖片
[Link](0) #等待按鍵被觸發後繼續
[Link]() #關閉所有顯示圖片的視窗
10. 高斯模糊
import cv2 as cv
img = [Link]("[Link]") #讀取圖片
ksize = 3 #模糊的範圍
gauss = [Link](img, (2*ksize+1, 2*ksize+1), 0) #做高斯
模糊
[Link]("GaussianBlur", gauss) #顯示圖片
[Link](0) #等待按鍵被觸發後繼續
[Link]() #關閉所有顯示圖片的視窗
[Link] 的 ksize 參數是一個 height*width 的資料型態,例如 3*3、
3*5,而且 height 和 width 必須為正奇數
11. 侵蝕
import cv2 as cv
import numpy as np
img = [Link]("[Link]") #讀取圖片
kernel = [Link]((3, 3), np.uint8) #產生 3*3 且預設值為 1 的矩陣
erode = [Link](img, kernel, iterations=1) #做 1 次侵蝕
[Link]("Erode", erode) #顯示圖片
[Link](0) #等待按鍵被觸發後繼續
[Link]() #關閉所有顯示圖片的視窗
12. 膨脹
import cv2 as cv
import numpy as np
img = [Link]("[Link]") #讀取圖片
kernel = [Link]((3, 3), np.uint8) #產生 3*3 且預設值為 1 的矩陣
dilate = [Link](img, kernel, iterations=1) #做 1 次膨脹
[Link]("Dilate", dilate) #顯示圖片
[Link](0) #等待按鍵被觸發後繼續
[Link]() #關閉所有顯示圖片的視窗
13. Canny 邊緣偵測
import cv2 as cv
img = [Link]("[Link]") #讀取圖片
gray = [Link](img, cv.COLOR_BGR2GRAY) #原圖轉灰階
_, threshold = [Link](gray, 128, 255, cv.THRESH_BINARY) #
做二值化
gauss = [Link](threshold, (3, 3), 0) #做高斯模糊
canny = [Link](gauss, 50, 100) #做 Canny
[Link]("Canny", canny) #顯示圖片
[Link](0) #等待按鍵被觸發後繼續
[Link]() #關閉所有顯示圖片的視窗
14. Hough Lines Transform
HoughLines(), 找出直線(無窮長)
import cv2 as cv
import numpy as np
img = [Link]("[Link]") #讀取圖片
gray = [Link](img, cv.COLOR_BGR2GRAY) #原圖轉灰階
h, w = [Link][:2]
canny = [Link](gray, 50, 150) #做 Canny
lines = [Link](canny, 1, [Link]/180, 100) #抓線
for line in lines:
for (rho, theta) in line: #計算位置
x0 = [Link](theta) * rho
y0 = [Link](theta) * rho
pt1 = (int(x0+(h+w)*(-[Link](theta))),
int(y0-(h+w)*[Link](theta)))
pt2 = (int(x0-(h+w)*(-[Link](theta))),
int(y0-(h+w)*[Link](theta)))
[Link](img, pt1, pt2, (0, 0, 255), 1) #畫線
[Link]("img", img) #顯示圖片
[Link](0) #等待按鍵被觸發後繼續
[Link]() #關閉所有顯示圖片的視窗
HoughLinesP(), 找出線段
import cv2 as cv
import numpy as np
img = [Link]("[Link]") #讀取圖片
gray = [Link](img, cv.COLOR_BGR2GRAY) #原圖轉灰階
canny = [Link](gray, 50, 150) #做 Canny
lines = [Link](canny, 1, [Link]/180, 100) #抓線
for line in lines:
for elem in line:
[Link](img, (elem[0], elem[1]), (elem[2], elem[3]), (0,
0, 255), 5) #畫線
[Link]("img", img) #顯示圖片
[Link](0) #等待按鍵被觸發後繼續
[Link]() #關閉所有顯示圖片的視窗
15. 尋找輪廓(Find Contours)
import cv2 as cv
import numpy as np
img = [Link]("[Link]") #讀取圖片
gray = [Link](img, cv.COLOR_BGR2GRAY) #原圖轉灰階
_, threshold = [Link](gray, 128, 255, cv.THRESH_BINARY) #
做二值化
contours, _ = [Link](threshold, cv.RETR_TREE,
cv.CHAIN_APPROX_SIMPLE) #抓輪廓
[Link](img, contours, -1, (0, 0, 255), 3) #畫輪廓
[Link]("img", img) #顯示圖片
[Link](0) #等待按鍵被觸發後繼續
[Link]() #關閉所有顯示圖片的視窗