1. 程式人生 > >Python2.7 + OpenCV3.4 縮放、高斯模糊、Canny邊緣提取

Python2.7 + OpenCV3.4 縮放、高斯模糊、Canny邊緣提取

摘要

因學習OpenCV需求,進行縮放、高斯模糊、Canny邊緣提取測試。

配置

系統:Windows7 x64
Python:2.7.14
PyCharm:2017.1.1
OpenCV:3.4.4

函式

影象縮放

輸入的影象存在大小不一定適配的問題,該函式通過設定寬、高閾值來進行等比例縮放。
輸入
1)讀入的影象;
2)寬閾值;
3)高閾值;
4)插值方法(可選)。
輸出
滿足寬、高閾值的影象。
示例
縮放後圖像

程式碼

def resizeImage(image, width, height, inter=cv2.INTER_AREA):
    '''
    影象縮放
    :param image: 輸入影象 
    :param width: 輸出影象寬限制
    :param height: 輸出影象高限制
    :param inter:  插值方法
                    CV_INTER_NN - 最近-鄰居插補
                    CV_INTER_LINEAR - 雙線性插值(預設方法)
                    CV_INTER_AREA - 像素面積相關重取樣。當縮小影象時,該方法可以避免波紋的出現。當放大影象時,類似於方法CV_INTER_NN
                    CV_INTER_CUBIC - 雙三次插值
    :return: 
    '''
    newsize = (width, height)
    # 獲取影象尺寸
    (h, w) = image.shape[:2]
    if w <= width and h <= height:
        return image
    # 高度算縮放比例
    if w > width:
        n = height / float(h)
        newsize = (int(n * w), height)
    else:
        n = width / float(w)
        newsize = (width, int(h * n))

    # 縮放影象
    newimage = cv2.resize(image, newsize, interpolation=inter)
    return newimage

高斯平滑+二值處理

將影象進行高斯平滑,並通過二值處理後輸出。
輸入
1)影象(RGB)。
輸出
1)高斯平滑後的二值圖。
示例
高斯平滑後的二值圖

程式碼

def gaussianBlur(filename):
    '''
    高斯平滑+二值圖
    :param 
            filename 檔名: 
    :param 
            type: 讀取圖片的方式
                IMREAD_COLOR 彩色影象
                IMREAD_GRAYSCALE 灰度影象
                IMREAD_ANYCOLOR 任意影象
    :return
            Gauss_img 高斯平滑+二值圖處理後的圖片: 
    '''
    gray_img = cv2.cvtColor(filename, cv2.COLOR_BGR2GRAY)
    Gauss_img = cv2.GaussianBlur(gray_img, (5,5), 0, 0, cv2.BORDER_DEFAULT)
    return Gauss_img

Canny邊緣提取

通過Canny邊緣檢測演算法提取邊緣,並輸出處理後的圖片
輸入
1)影象(灰度圖)。
輸出
1)經過Canny邊緣提取的圖片。
示例
經過Canny邊緣提取的圖片

程式碼

def cannyFindBoundary(img):
    '''
    Canny邊緣提取
    :param img: 圖片
    :return: Canny Canny邊緣提取後的影象
    '''


    Canny = cv2.Canny(img, 200, 300)
    return Canny

等待函式

暫停,直到按下任意鍵後,關閉所有視窗。
輸入
1)任意按鍵。
輸出
1)所有視窗都關閉。
程式碼

def wait():
    cv2.waitKey()
    cv2.destroyAllWindows()

整體程式碼

# encoding: utf-8
'''
    Author:MyoontyeeChen
    Date:20181202
    Python2.7 + OpenCV3.4 縮放、高斯模糊、Canny邊緣提取
'''
import cv2

def resizeImage(image, width, height, inter=cv2.INTER_AREA):
    '''
    影象縮放
    :param image: 輸入影象 
    :param width: 輸出影象寬限制
    :param height: 輸出影象高限制
    :param inter:  插值方法
                    CV_INTER_NN - 最近-鄰居插補
                    CV_INTER_LINEAR - 雙線性插值(預設方法)
                    CV_INTER_AREA - 像素面積相關重取樣。當縮小影象時,該方法可以避免波紋的出現。當放大影象時,類似於方法CV_INTER_NN
                    CV_INTER_CUBIC - 雙三次插值
    :return: 
    '''
    newsize = (width, height)
    # 獲取影象尺寸
    (h, w) = image.shape[:2]
    if w <= width and h <= height:
        return image
    # 高度算縮放比例
    if w > width:
        n = height / float(h)
        newsize = (int(n * w), height)
    else:
        n = width / float(w)
        newsize = (width, int(h * n))

    # 縮放影象
    newimage = cv2.resize(image, newsize, interpolation=inter)
    return newimage

def gaussianBlur(filename):
    '''
    高斯平滑+二值圖
    :param 
            filename 檔名: 
    :param 
            type: 讀取圖片的方式
                IMREAD_COLOR 彩色影象
                IMREAD_GRAYSCALE 灰度影象
                IMREAD_ANYCOLOR 任意影象
    :return
            Gauss_img 高斯平滑+二值圖處理後的圖片: 
    '''
    gray_img = cv2.cvtColor(filename, cv2.COLOR_BGR2GRAY)
    Gauss_img = cv2.GaussianBlur(gray_img, (5,5), 0, 0, cv2.BORDER_DEFAULT)
    return Gauss_img

def cannyFindBoundary(img):
    '''
    Canny邊緣提取
    :param img: 圖片
    :return: Canny Canny邊緣提取後的影象
    '''


    Canny = cv2.Canny(img, 200, 300)
    return Canny

def wait():
    cv2.waitKey()
    cv2.destroyAllWindows()

def main():
    img = cv2.imread("i8.jpg",1)
    img =resizeImage(img,300,300)
    cv2.imshow("img", img)
    Gauss_img = gaussianBlur(img)
    cv2.imshow("Gauss_img",Gauss_img)
    Canny = cannyFindBoundary(img)
    cv2.imshow("Canny",Canny)
    wait()

main()

出現問題

除錯如下程式碼

gray_img = cv2.cvtColor(filename, cv2.COLOR_BGR2GRAY)

可能出現如下問題

Traceback (most recent call last):
  File "E:/PythonExe/OpenCV/Exe1.py", line 61, in <module>
    main()
  File "E:/PythonExe/OpenCV/Exe1.py", line 55, in main
    gray_img = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
cv2.error: OpenCV(3.4.4) c:\projects\opencv-python\opencv\modules\imgproc\src\color.hpp:255: error: (-2:Unspecified error) in function '__thiscall cv::CvtHelper<struct cv::Set<3,4,-1>,struct cv::Set<1,-1,-1>,struct cv::Set<0,2,5>,2>::CvtHelper(const class cv::_InputArray &,const class cv::_OutputArray &,int)'
> Invalid number of channels in input image:
>     'VScn::contains(scn)'
> where
>     'scn' is 1

問題原因
在下述命令中,第二個引數“0”使得讀入圖片為灰度圖
輸入的影象是灰度圖,不是RGB圖

img = cv2.imread(filename, 0)

解決方法
按如下方式修改上述命令,其中filename需修改為要提取的圖片檔名。

img = cv2.imread(filename, 1)

參考

程式碼
[1]opencv3 影象處理 之 影象縮放( python與c++實現 )
[2]cvResize
[3]OpenCV3程式設計入門筆記(1)影象載入、顯示、儲存、變換灰度圖
[4]opencv學習(十六)之顏色空間轉換cvtColor()
圖片
處理前圖片為寶馬i8影象,來自如下網址,如侵權請告知我,立馬刪除。
[1]寶馬i8釋出會