1. 程式人生 > >opencv(9)-物件檢測+膨脹與腐蝕

opencv(9)-物件檢測+膨脹與腐蝕

物件檢測:前提是輪廓檢測

程式碼:

# -*- coding=GBK -*-
import cv2
import numpy as np

# approxPolyDP(curve, epsilon, closed[, approxCurve]) -> approxCurve
def measure_object(image):
    # 輪廓檢測
    gray = cv2.cvtColor(image,cv2.COLOR_BGR2GRAY)
    ret,binary = cv2.threshold(gray,0,255,cv2.THRESH_BINARY | cv2.THRESH_OTSU)
    cv2.imshow('binary',binary)
    outImage,contours,hireachy = cv2.findContours(binary,cv2.RETR_EXTERNAL,cv2.CHAIN_APPROX_SIMPLE)
    for contour in contours:
        area = cv2.contourArea(contour) # 計算輪廓面積
        x,y,w,h = cv2.boundingRect(contour) # 計算外切矩形
        M = cv2.moments(contour) # 求其幾何矩
        # 求其重心座標
        if M['m00']!=0:
            cx=int(M['m10']/M['m00'])
            cy=int(M['m01']/M['m00'])
        else:
            cx,cy = 0,0
        # 畫出重心座標
        cv2.circle(image,(np.int(cx),np.int(cy)),3,(0,255,255),-1) # -1 填充
        # 畫出外切矩形
        cv2.rectangle(image,(x,y),(x+w,y+h),(0,0,255),2)
    cv2.imshow('measure_contour',image)

img = cv2.imread('numbers.jpg',1)
cv2.imshow('src',img)
measure_object(img)
cv2.waitKey(0)
cv2.destroyAllWindows()

結果

# -*- coding=GBK -*-
import cv2
import numpy as np

# approxPolyDP(curve, epsilon, closed[, approxCurve]) -> approxCurve
def measure_object(image):
    # 輪廓檢測
    gray = cv2.cvtColor(image,cv2.COLOR_BGR2GRAY)
    ret,binary = cv2.threshold(gray,0,255,cv2.THRESH_BINARY_INV | cv2.THRESH_OTSU)
    cv2.imshow('binary',binary)
    # 將輪廓顯示到二值圖形上去,用approxCurve函式的shape[0]區分圖片形狀,例如4是方形,3是三角形,這裡數字是擬合的折線條數
    dst = cv2.cvtColor(binary,cv2.COLOR_GRAY2BGR)
    outImage,contours,hireachy = cv2.findContours(binary,cv2.RETR_EXTERNAL,cv2.CHAIN_APPROX_SIMPLE)
    for i,contour in enumerate(contours):
        area = cv2.contourArea(contour) # 計算輪廓面積
        x,y,w,h = cv2.boundingRect(contour) # 計算外切矩形
        M = cv2.moments(contour) # 求其幾何矩
        # 求其重心座標
        if M['m00']!=0:
            cx=int(M['m10']/M['m00'])
            cy=int(M['m01']/M['m00'])
        else:
            cx,cy = 0,0
        # 畫出重心座標
        cv2.circle(dst,(np.int(cx),np.int(cy)),3,(0,255,255),-1) # -1 填充
        # 畫出外切矩形
        cv2.rectangle(dst,(x,y),(x+w,y+h),(0,0,255),2)
        
        # 多邊形擬合,可以用來分出圖形,主要是依靠每個圖形的邊緣需要多少折線擬合
        approxCurve = cv2.approxPolyDP(contour,4,True)
        if approxCurve.shape[0]>4:
            cv2.drawContours(dst,contour,i,(0,255,0),2)
    cv2.imshow('measure_contour',image)

img = cv2.imread('haha.png',1)
cv2.imshow('src',img)
measure_object(img)
cv2.waitKey(0)
cv2.destroyAllWindows()

膨脹與腐蝕

影象形態學:處理灰度和二值影象

膨脹:或 or

程式碼:

# -*- coding=GBK -*-
import cv2
import numpy as np

# approxPolyDP(curve, epsilon, closed[, approxCurve]) -> approxCurve
def dilate_demo(image):
    # 輪廓檢測
    gray = cv2.cvtColor(image,cv2.COLOR_BGR2GRAY)
    ret,binary = cv2.threshold(gray,0,255,cv2.THRESH_BINARY | cv2.THRESH_OTSU)
    cv2.imshow('binary',binary)
    # getStructuringElement(shape, ksize[, anchor]) -> retval 
    # 獲取結構型元素,用來 膨脹或者腐蝕, shape=cv2.MORPH_RECT/cv2.MORPH_CROSS等
    kernel = cv2.getStructuringElement(cv2.MORPH_RECT,(5,5)) # ksize 可以認為腐蝕或膨脹強度,越大,腐蝕越大
    dst = cv2.dilate(binary,kernel)
    cv2.imshow('dilate_demo',dst)
    
img = cv2.imread('numbers.jpg',1)
cv2.imshow('src',img)
dilate_demo(img)
cv2.waitKey(0)
cv2.destroyAllWindows()

結果:

腐蝕:與 and

程式碼:

# -*- coding=GBK -*-
import cv2
import numpy as np

# approxPolyDP(curve, epsilon, closed[, approxCurve]) -> approxCurve
def erode_demo(image):
    # 輪廓檢測
    gray = cv2.cvtColor(image,cv2.COLOR_BGR2GRAY)
    ret,binary = cv2.threshold(gray,0,255,cv2.THRESH_BINARY | cv2.THRESH_OTSU)
    cv2.imshow('binary',binary)
    # getStructuringElement(shape, ksize[, anchor]) -> retval 
    # 獲取結構型元素,用來 膨脹或者腐蝕, shape=cv2.MORPH_RECT/cv2.MORPH_CROSS等
    kernel = cv2.getStructuringElement(cv2.MORPH_RECT,(5,5)) # ksize 可以認為腐蝕或膨脹強度,越大,腐蝕越大
    dst = cv2.erode(binary,kernel)
    cv2.imshow('erode_demo',dst)
    
img = cv2.imread('numbers.jpg',1)
cv2.imshow('src',img)
erode_demo(img)
cv2.waitKey(0)
cv2.destroyAllWindows()

結果: