Python OpenCV閾值處理詳解
前言
圖像分割是許多計(jì)算機(jī)視覺(jué)應(yīng)用中的關(guān)鍵處理步驟,通常用于將圖像劃分為不同的區(qū)域,這些區(qū)域常常對(duì)應(yīng)于真實(shí)世界的對(duì)象。因此,圖像分割是圖像識(shí)別和內(nèi)容分析的重要步驟。圖像閾值是一種簡(jiǎn)單、有效的圖像分割方法,其中像素根據(jù)其強(qiáng)度值進(jìn)行分區(qū)。在本文中,將介紹 OpenCV
所提供的主要閾值技術(shù),可以將這些技術(shù)用作計(jì)算機(jī)視覺(jué)應(yīng)用程序中圖像分割的關(guān)鍵部分。
閾值技術(shù)簡(jiǎn)介
閾值處理是一種簡(jiǎn)單、有效的將圖像劃分為前景和背景的方法。圖像分割通常用于根據(jù)對(duì)象的某些屬性(例如,顏色、邊緣或直方圖)從背景中提取對(duì)象。最簡(jiǎn)單的閾值方法會(huì)利用預(yù)定義常數(shù)(閾值),如果像素強(qiáng)度小于閾值,則用黑色像素替換,如果像素強(qiáng)度大于閾值,則用白色像素替換。OpenCV 提供了 cv2.threshold()
函數(shù)來(lái)對(duì)圖像進(jìn)行閾值處理。
為了測(cè)試 cv2.threshold()
函數(shù),首次創(chuàng)建測(cè)試圖像,其包含一些填充了不同的灰色調(diào)的大小相同的區(qū)域,利用 build_sample_image()
函數(shù)構(gòu)建此測(cè)試圖像:
def build_sample_image(): """創(chuàng)建填充了不同的灰色調(diào)的大小相同的區(qū)域,作為測(cè)試圖像""" # 定義不同區(qū)域 tones = np.arange(start=50, stop=300, step=50) # 初始化 result = np.zeros((50, 50, 3), dtype="uint8") for tone in tones: img = np.ones((50, 50, 3), dtype="uint8") * tone # 沿軸連接數(shù)組 result = np.concatenate((result, img), axis=1) return result
接下來(lái)將使用不同的預(yù)定義閾值: 0 、 50 、 100 、 150 、 200 和 250 調(diào)用 cv2.threshold()
函數(shù),以查看不同預(yù)定義閾值對(duì)閾值圖像影響。例如,使用閾值 thresh = 50
對(duì)圖像進(jìn)行閾值處理:
ret1, thresh1 = cv2.threshold(gray_image, 50, 255, cv2.THRESH_BINARY)
其中,thresh1
是僅包含黑白色的閾值圖像。源圖像 gray_image
中灰色強(qiáng)度小于 50 的像素為黑色,強(qiáng)度大于 50 的像素為白色。
使用多個(gè)不同閾值對(duì)圖像進(jìn)行閾值處理:
# 可視化函數(shù) def show_img_with_matplotlib(color_img, title, pos): img_RGB = color_img[:, :, ::-1] ax = plt.subplot(7, 1, pos) plt.imshow(img_RGB) plt.title(title, fontsize=8) plt.axis('off') # 使用 build_sample_image() 函數(shù)構(gòu)建測(cè)試圖像 image = build_sample_image() gray_image = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY) for i in range(6): # 使用多個(gè)不同閾值對(duì)圖像進(jìn)行閾值處理 ret, thresh = cv2.threshold(gray_image, 50 * i, 255, cv2.THRESH_BINARY) # 可視化 show_img_with_matplotlib(cv2.cvtColor(thresh, cv2.COLOR_GRAY2BGR), "threshold = {}".format(i * 50), i + 2) # 可視化測(cè)試圖像 show_img_with_matplotlib(cv2.cvtColor(gray_image, cv2.COLOR_GRAY2BGR), "img with tones of gray - left to right: (0,50,100,150,200,250)", 1) # 圖像進(jìn)行閾值處理后,常見(jiàn)的輸出是黑白圖像 # 因此,為了更好的可視化效果,修改背景顏色 fig.patch.set_facecolor('silver') plt.show()
從上圖可以看出,根據(jù)閾值和樣本圖像灰度值的不同,閾值處理后生成的黑白圖像的變化情況。
簡(jiǎn)單的閾值技術(shù)
上一節(jié)中,我們已經(jīng)簡(jiǎn)單介紹過(guò)了 OpenCV
中提供的簡(jiǎn)單閾值處理函數(shù)——cv2.threshold()
,該函數(shù)用法如下:
cv2.threshold(src, thresh, maxval, type, dst=None) -> retval, dst
cv2.threshold()
函數(shù)對(duì) src
輸入數(shù)組(可以為單通道或多通道圖像)應(yīng)用預(yù)定義常數(shù) thresh
設(shè)置的閾值;type
參數(shù)用于設(shè)置閾值類(lèi)型,閾值類(lèi)型的可選值如下:cv2.THRESH_BINARY
、cv2.THRESH_BINARY_INV
、cv2.THRESH_TRUNC
、cv2.THRESH_TOZERO
、cv2.THRESH_TOZERO_INV
、cv2.THRESH_OTSU
和 cv2.THRESH_TRIANGLE
。
maxval
參數(shù)用于設(shè)置最大值,其僅在閾值類(lèi)型為 cv2.THRESH_BINARY
和 cv2.THRESH_BINARY_INV
時(shí)有效;需要注意的是,在閾值類(lèi)型為 cv2.THRESH_OTSU
和 cv2.THRESH_TRIANGLE
時(shí),輸入圖像 src
應(yīng)為為單通道。
閾值類(lèi)型
為了更好的了解閾值操作的不同類(lèi)型,接下來(lái)給出每種閾值類(lèi)型的具體公式。符號(hào)說(shuō)明:src
是源(原始)圖像,dst
對(duì)應(yīng)于閾值化后的目標(biāo)(結(jié)果)圖像,因此,src(x, y)
對(duì)應(yīng)于源圖像像素 (x, y)
處的強(qiáng)度,而 dst(x, y)
對(duì)應(yīng)于目標(biāo)圖像像素 (x, y)
處的強(qiáng)度。
閾值類(lèi)型 cv2.THRESH_BINARY
公式如下:
其表示,如果像素 src(x, y)
的強(qiáng)度高于 thresh
,則目標(biāo)圖像像素強(qiáng)度 dst(x,y)
將被設(shè)為 maxval
;否則,設(shè)為 0
。
閾值類(lèi)型 cv2.THRESH_BINARY_INV
公式如下:
其表示,如果像素 src(x, y)
的強(qiáng)度高于 thresh
,則目標(biāo)圖像像素強(qiáng)度 dst(x,y)
將被設(shè)為 0
;否則,設(shè)為 maxval
。
閾值類(lèi)型 cv2.THRESH_TRUNC
公式如下:
其表示,如果像素 src(x, y)
的強(qiáng)度高于 thresh
,則目標(biāo)圖像像素強(qiáng)度設(shè)置為 threshold
;否則,設(shè)為 src(x, y)
。
閾值類(lèi)型 cv2.THRESH_TOZERO
公式如下:
其表示,如果像素 src(x, y)
的強(qiáng)度高于 thresh
,則目標(biāo)圖像像素值將設(shè)置為 src(x, y)
;否則,設(shè)置為 0
。
閾值類(lèi)型 cv2.THRESH_TOZERO_INV
公式如下:
其表示,如果像素 src(x, y)
的強(qiáng)度大于 thresh
,則目標(biāo)圖像像素值將設(shè)置為 0
;否則,設(shè)置為 src(x, y)
。
而 cv2.THRESH_OTSU
和 cv2.THRESH_TRIANGLE
屬于特殊的閾值類(lèi)型,它們可以與上述閾值類(lèi)型( cv2.THRESH_BINARY
、cv2.THRESH_BINARY_INV
、cv2.THRESH_TRUNC
、cv2.THRESH_TOZERO
和 cv2.THRESH_TOZERO_INV
)進(jìn)行組合。組合后,閾值處理函數(shù) cv2.threshold()
將只能處理單通道圖像,且計(jì)算并返回最佳閾值,而非指定閾值。
接下來(lái)使用不同閾值類(lèi)型對(duì)同樣的測(cè)試圖像進(jìn)行閾值處理,觀察不同閾值處理效果:
ret1, thresh1 = cv2.threshold(gray_image, 100, 255, cv2.THRESH_BINARY) ret2, thresh2 = cv2.threshold(gray_image, 100, 220, cv2.THRESH_BINARY) ret3, thresh3 = cv2.threshold(gray_image, 100, 255, cv2.THRESH_BINARY_INV) ret4, thresh4 = cv2.threshold(gray_image, 100, 220, cv2.THRESH_BINARY_INV) ret5, thresh5 = cv2.threshold(gray_image, 100, 255, cv2.THRESH_TRUNC) ret6, thresh6 = cv2.threshold(gray_image, 100, 255, cv2.THRESH_TOZERO) ret7, thresh7 = cv2.threshold(gray_image,100,255, cv2.THRESH_TOZERO_INV) # 可視化 show_img_with_matplotlib(cv2.cvtColor(thresh1, cv2.COLOR_GRAY2BGR), "THRESH_BINARY - thresh = 100 & maxValue = 255", 2) show_img_with_matplotlib(cv2.cvtColor(thresh2, cv2.COLOR_GRAY2BGR), "THRESH_BINARY - thresh = 100 & maxValue = 220", 3) show_img_with_matplotlib(cv2.cvtColor(thresh3, cv2.COLOR_GRAY2BGR), "THRESH_BINARY_INV - thresh = 100", 4) # 其他圖像可視化方法類(lèi)似,不再贅述 # ...
如上圖所示,maxval
參數(shù)僅在使用 cv2.THRESH_BINARY
和 cv2.THRESH_BINARY_INV
閾值類(lèi)型時(shí)有效,上例中將 cv2.THRESH_BINARY
和 cv2.THRESH_BINARY_INV
類(lèi)型的 maxval
值設(shè)置為 255
及 220
,以便查看閾值圖像在這兩種情況下的變化情況。
簡(jiǎn)單閾值技術(shù)的實(shí)際應(yīng)用
了解 cv2.threshold()
不同參數(shù)的工作原理后,我們將 cv2.threshold()
應(yīng)用于真實(shí)圖像,并使用不同的閾值:
# 加載圖像 image = cv2.imread('example.png') gray_image = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY) # 繪制灰度圖像 show_img_with_matplotlib(cv2.cvtColor(gray_image, cv2.COLOR_GRAY2BGR), "img", 1) # 使用不同的閾值調(diào)用 cv2.threshold() 并進(jìn)行可視化 for i in range(8): ret, thresh = cv2.threshold(gray_image, 130 + i * 10, 255, cv2.THRESH_BINARY) show_img_with_matplotlib(cv2.cvtColor(thresh, cv2.COLOR_GRAY2BGR), "threshold = {}".format(130 + i * 10), i + 2)
以上就是Python OpenCV閾值處理詳解的詳細(xì)內(nèi)容,更多關(guān)于OpenCV閾值處理的資料請(qǐng)關(guān)注腳本之家其它相關(guān)文章!
相關(guān)文章
Python讀取圖片EXIF信息類(lèi)庫(kù)介紹和使用實(shí)例
這篇文章主要介紹了Python讀取圖片EXIF信息類(lèi)庫(kù)介紹和使用實(shí)例,例如Python Imaging Library、EXIF.py等,需要的朋友可以參考下2014-07-07基于 Python實(shí)現(xiàn)云服務(wù)器的CDN域名遠(yuǎn)程鑒權(quán)配置
這篇文章主要介紹了基于 Python實(shí)現(xiàn)云服務(wù)器的CDN域名遠(yuǎn)程鑒權(quán)配置,文章內(nèi)容技術(shù)詳細(xì),具有一定的參考價(jià)值,需要的小伙伴可以參考一下2022-05-05基于Python編寫(xiě)一個(gè)根據(jù)姓名測(cè)性別的小程序
這篇文章主要為大家介紹了如何利用Python編寫(xiě)一款根據(jù)中文名能猜測(cè)性別的一款界面化的小程序,文中的示例代碼講解詳細(xì),感興趣的小伙伴可以了解一下2022-03-03python編程使用selenium模擬登陸淘寶實(shí)例代碼
這篇文章主要介紹了python編程使用selenium模擬登陸淘寶實(shí)例代碼,涉及selenium的簡(jiǎn)介及Windows下的安裝,分享了相關(guān)代碼示例,小編覺(jué)得還是挺不錯(cuò)的,具有一定借鑒價(jià)值,需要的朋友可以參考下2018-01-01Python中讓MySQL查詢結(jié)果返回字典類(lèi)型的方法
這篇文章主要介紹了Python中讓MySQL查詢結(jié)果返回字典類(lèi)型的方法,默認(rèn)情況下Mysql返回的是元組類(lèi)型,本文實(shí)現(xiàn)了返回字典類(lèi)型,需要的朋友可以參考下2014-08-08python opencv檢測(cè)目標(biāo)顏色的實(shí)例講解
下面小編就為大家分享一篇python opencv檢測(cè)目標(biāo)顏色的實(shí)例講解,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。一起跟隨小編過(guò)來(lái)看看吧2018-04-04