激情久久久_欧美视频区_成人av免费_不卡视频一二三区_欧美精品在欧美一区二区少妇_欧美一区二区三区的

腳本之家,腳本語言編程技術及教程分享平臺!
分類導航

Python|VBS|Ruby|Lua|perl|VBA|Golang|PowerShell|Erlang|autoit|Dos|bat|

服務器之家 - 腳本之家 - Python - Python 計算機視覺編程進階之OpenCV 進行霍夫變換

Python 計算機視覺編程進階之OpenCV 進行霍夫變換

2022-03-07 00:21一馬歸一碼 Python

霍夫變換(Hough)是一個非常重要的檢測間斷點邊界形狀的方法。它通過將圖像坐標空間變換到參數空間,來實現直線與曲線的擬合,通過本篇文章我們來詳細了解它

參考的一些文章以及論文我都會給大家分享出來 —— 鏈接就貼在原文,論文我上傳到資源中去,大家可以免費下載學習,如果當天資源區找不到論文,那就等等,可能正在審核,審核完后就可以下載了。大家一起學習,一起進步!加油!!

前言

(1)讀取圖像信息

經典操作,不必多說:

"""
Author:XiaoMa
date:2021/11/13
"""
import cv2
import matplotlib.pyplot as plt
import numpy as np

img0 = cv2.imread("E:\From Zhihu\For the desk\cvfourteen1.jpg")
img1 = cv2.cvtColor(img0, cv2.COLOR_BGR2GRAY)
h, w = img0.shape[:2]
print(h, w)
cv2.imshow("W0", img0)
cv2.imshow("W1", img1)
cv2.waitKey(delay = 0)

Python 計算機視覺編程進階之OpenCV 進行霍夫變換

Python 計算機視覺編程進階之OpenCV 進行霍夫變換

525 787

(2)霍夫變換的目的及應用

經典的霍夫變換是被用來檢測圖像中的直線,后來擴展到任何形狀的檢測識別中,多為直線和橢圓。所以利用霍夫變換我們可以提取圖像中的直線以及其他形狀類型的線條。

 

1. 霍夫變換

霍夫變換是圖像處理中的一種特征提取技術,它通過一種投票算法檢測具有特定形狀的物體。該過程在一個參數空間中通過計算累計結果的局部最大值得到一個符合該特定形狀的集合作為霍夫變換的結果。

霍夫變換運用兩個坐標空間的變換將在一個空間中具有相同形狀的曲線或者直線映射到另外一個空間的坐標點上形成峰值,從而把檢測任意形狀的問題轉化為統計峰值的問題。

 

2. 霍夫線變換

(1)基本概念

我們一般理解的在笛卡爾坐標系中表示直線的方式有點線式和兩點式,然而在霍夫變換中,考慮的卻是另外一種方式:使用 (r, theta) 表示一條直線,其中 r 代表原點到這條直線的距離,theta 表示該直線的垂線與 x 軸的夾角。

Python 計算機視覺編程進階之OpenCV 進行霍夫變換

那么我們怎么檢測直線呢?首先我們為每一個點假設 n 個方向的直線,一般 n 為180,這樣檢測直線的角度精度為 1 度,分別計算這 n 條直線的(r, theta)坐標,得到 n 個坐標點。那么判斷 N 個坐標點就得到 N*n 個 (r, theta)坐標,其中 theta 是離散的角度,有180個取值。當多個點在同一條直線上時,那么這條直線可以通過這些點中的任意一個點的某一個(r_i, theta_i)表示出來(每一個點取到特定的 theta 時得到的 r 相等或者相近)。比如空間中有三個點,下圖表示了判斷這三個點共線的方式:

Python 計算機視覺編程進階之OpenCV 進行霍夫變換

可以看出當 Angel(theta) 為 60 時距離 (r) 大致都為80.7,由此可以判斷這三個點都在直線(80.7,60)上。

我們也可以繪制一幅 r-theta 坐標系,每一個點的 theta 為橫坐標軸,r 為縱坐標,當不同的點出現交點說明這兩個點在同一條直線上:

Python 計算機視覺編程進階之OpenCV 進行霍夫變換

(2)代碼實現

本例中使用到了邊緣檢測來減少計算,如果有小伙伴對邊緣檢測不熟悉可以去參考我之前的文章:

Python 計算機視覺編程進階之OpenCV 圖像銳化及邊緣檢測

如果對函數的參數有疑問的話可以參考官網:OpenCV

對于下面的代碼,我都添加注釋了,應該講清楚了,如果有注釋的不清楚的地方,可以在評論區指出來,大家一起討論

#霍夫直線檢測
##首先進行邊緣檢測,來減少空間中其他的點帶來的計算量的問題
img2 = cv2.GaussianBlur(img1, (5, 5), 0)   #高斯模糊為邊緣檢測做準備
img3 = cv2.Canny(img2, 50, 120)            #使用Canny算子進行邊緣檢測
cv2.imshow("W2", img3)
cv2.waitKey(delay = 0)
rho = 1                    #距離分辨率
theta = np.pi/180          #角度分辨率
threshold = 10             #霍夫空間中多少個曲線相交表示一個正式的交點
min_line_len = 50          #最少需要多少個像素點才構成一條直線
max_line_gap = 50          #線段之間的最大間隔像素點數
lines = cv2.HoughLinesP(img3, rho, theta, threshold, maxLineGap = max_line_gap)    #所以這個函數中的參數都已經在前面賦值時解釋過了
img4 = np.zeros_like(img3)
for line in lines:
  for x1, y1, x2, y2 in line:
      cv2.line(img4, (x1, y1), (x2, y2), 255, 1)        #繪制直線
cv2.imshow("W3", img4)
cv2.waitKey(delay = 0)

得到的邊緣檢測圖像為:

Python 計算機視覺編程進階之OpenCV 進行霍夫變換

得到的霍夫直線檢測的圖像為:

Python 計算機視覺編程進階之OpenCV 進行霍夫變換

當然霍夫直線檢測用在其他的比如建筑等方面才是好鋼用在刀刃上,這里作為示范用了人像。

 

3. 霍夫圓變換

(1)基本概念

一般來說,表示一個圓需要知道它的半徑以及圓心,這樣我們需要 (x, y, r) 三個參數,如果只是靠這種方法識別圓,那么對于計算機來說計算效率會下降。

在 OpenCV 中是使用了霍夫梯度的方法,利用邊界梯度信息。首先使用 Canny() 進行邊緣檢測,對邊緣的每一個非 0 通過 Sobel() 進行局部梯度計算(Sobel() 算子也在前面的文章中介紹過了),得到的梯度方向就是圓切線的方向,得到3個切線就可以確定圓心了。

(2)代碼實現

已添加注釋:

#霍夫圓檢測
dp = 1              #檢測內測圓心的累加器圖像的分辨率與輸入圖像之比的倒數
minDist = 700       #兩個圓之間圓心之間的最小距離
param1 = 100        #前面提到過 Canny 邊緣檢測,這個參數表示傳遞給邊緣檢測的高閾值
param2 = 80         #檢測階段圓心的累加器閾值,簡單來說該參數越大檢測到的圓越完美,但數目越少,反之亦然
minRadius = 10      #最小圓的半徑
maxRadius = 20      #最大圓的半徑
cirlces = cv2.HoughCircles(img2, cv2.HOUGH_GRADIENT, dp, minDist, param1, param2, minRadius, maxRadius)  #函數的參數前面解釋過了
cirlces = np.uint16(np.around(cirlces))
for i in cirlces[0, :]:
  cv2.circle(img0, (i[0], i[1]), i[2], (0, 0, 255), 1)
  cv2.circle(img0, (i[0], i[1]), 2, (0, 0, 255), 1)
cv2.imshow("W4", img0)
cv2.waitKey(delay = 0)

Python 計算機視覺編程進階之OpenCV 進行霍夫變換

可以看出對人像的檢測局限于頭部,哈哈哈哈,建議大家多改幾次參數進行嘗試,會得到不一樣的體驗,也可以多換幾張圖進行測試。

 

4. 將所有圖像繪制到一張圖中

都是一些常規問題,沒啥好注釋的

#將所有圖像繪制在一張圖紙上
img0 = cv2.imread("E:\From Zhihu\For the desk\cvfourteen1.jpg")   #再次讀取原圖,前面的圖像已經進行了變換
plt.rcParams['font.family'] = 'SimHei'       #將全局中文字體改為黑體
imgs = [img0, img1, img2, img3, img4, img5]
title = ['原圖', '灰度圖', '高斯模糊', '邊緣檢測', '霍夫直線檢測', '霍夫圓檢測']
for i in range(6):
  imgs[i] = cv2.cvtColor(imgs[i], cv2.COLOR_BGR2RGB)
  plt.subplot(2, 3, i + 1)
  plt.imshow(imgs[i])
  plt.title(title[i])
  plt.xticks([])
  plt.yticks([])
plt.show()

Python 計算機視覺編程進階之OpenCV 進行霍夫變換

 

5. 總體代碼

修改圖像路徑就可以用了,但還是建議小伙伴們一步步來。

"""
Author:XiaoMa
date:2021/11/13
"""
import cv2
import matplotlib.pyplot as plt
import numpy as np

img0 = cv2.imread("E:\From Zhihu\For the desk\cvfourteen1.jpg")
#img0 = cv2.resize(img0, dsize = None, fx = 0.5, fy = 0.5)
img1 = cv2.cvtColor(img0, cv2.COLOR_BGR2GRAY)
h, w = img0.shape[:2]
print(h, w)
cv2.imshow("W0", img0)
cv2.imshow("W1", img1)
cv2.waitKey(delay = 0)
#霍夫直線檢測
##首先進行邊緣檢測,來減少空間中其他的點帶來的計算量的問題
img2 = cv2.GaussianBlur(img1, (5, 5), 0)   #高斯模糊為邊緣檢測做準備
img3 = cv2.Canny(img2, 50, 120)            #使用Canny算子進行邊緣檢測
cv2.imshow("W2", img3)
cv2.waitKey(delay = 0)
rho = 1                    #距離分辨率
theta = np.pi/180          #角度分辨率
threshold = 10             #霍夫空間中多少個曲線相交表示一個正式的交點
min_line_len = 50          #最少需要多少個像素點才構成一條直線
max_line_gap = 50          #線段之間的最大間隔像素點數
lines = cv2.HoughLinesP(img3, rho, theta, threshold, maxLineGap = max_line_gap)    #所以這個函數中的參數都已經在前面賦值時解釋過了
img4 = np.zeros_like(img3)
for line in lines:
  for x1, y1, x2, y2 in line:
      cv2.line(img4, (x1, y1), (x2, y2), 255, 1)        #繪制直線
cv2.imshow("W3", img4)
cv2.waitKey(delay = 0)
#霍夫圓檢測
dp = 1              #檢測內測圓心的累加器圖像的分辨率與輸入圖像之比的倒數
minDist = 700       #兩個圓之間圓心之間的最小距離
param1 = 100        #前面提到過 Canny 邊緣檢測,這個參數表示傳遞給邊緣檢測的高閾值
param2 = 80         #檢測階段圓心的累加器閾值,簡單來說該參數越大檢測到的圓越完美,但數目越少,反之亦然
minRadius = 10      #最小圓的半徑
maxRadius = 20      #最大圓的半徑
cirlces = cv2.HoughCircles(img2, cv2.HOUGH_GRADIENT, dp, minDist, param1, param2, minRadius, maxRadius)  #函數的參數前面解釋過了
cirlces = np.uint16(np.around(cirlces))
img5 = img0
for i in cirlces[0, :]:
  cv2.circle(img5, (i[0], i[1]), i[2], (0, 0, 255), 1)
  cv2.circle(img5, (i[0], i[1]), 2, (0, 0, 255), 1)
cv2.imshow("W4", img5)
cv2.waitKey(delay = 0)
#將所有圖像繪制在一張圖紙上
img0 = cv2.imread("E:\From Zhihu\For the desk\cvfourteen1.jpg")   #再次讀取原圖,前面的圖像已經進行了變換
plt.rcParams['font.family'] = 'SimHei'       #將全局中文字體改為黑體
imgs = [img0, img1, img2, img3, img4, img5]
title = ['原圖', '灰度圖', '高斯模糊', '邊緣檢測', '霍夫直線檢測', '霍夫圓檢測']
for i in range(6):
  imgs[i] = cv2.cvtColor(imgs[i], cv2.COLOR_BGR2RGB)
  plt.subplot(2, 3, i + 1)
  plt.imshow(imgs[i])
  plt.title(title[i])
  plt.xticks([])
  plt.yticks([])
plt.show()

 

結束語

本文主要總結了霍夫變換的基本概念和代碼實現,包括線變換和圓變換,建議大家多嘗試,一些參數什么的多修改多試試。本篇文章主要參考的是《Python計算機視覺》這邊書,清華大學出版的,大家感興趣可以找來看看。

到此這篇關于Python 計算機視覺編程進階之OpenCV 進行霍夫變換的文章就介紹到這了,更多相關Python OpenCV 霍夫變換內容請搜索服務器之家以前的文章或繼續瀏覽下面的相關文章希望大家以后多多支持服務器之家!

原文鏈接:https://blog.csdn.net/qq_52309640/article/details/120941305

延伸 · 閱讀

精彩推薦
主站蜘蛛池模板: 欧美精品一区二区三区四区 | 国产精品成人av片免费看最爱 | 久久久久久久久久久久久久av | 宅男噜噜噜66国产在线观看 | 欧美一级一片 | 看一级毛片 | 国产精品视频自拍 | 亚洲人成中文字幕在线观看 | 特黄一级小说 | www深夜成人 | 看一级毛片 | 九九精品在线播放 | 久久成人免费网站 | 久久亚洲国产午夜精品理论片 | av性色全交蜜桃成熟时 | 一区二区久久精品66国产精品 | 国产成人精品一区在线播放 | 日本免费不卡一区二区 | 亚洲片在线观看 | 一本色道久久综合狠狠躁篇适合什么人看 | 99ri精品 | 黄色网址免费在线播放 | 欧美精品一级 | 宅男噜噜噜66一区二区 | 亚洲成人激情在线 | 国产毛片视频在线 | 在线看三级 | 久久网站热最新地址4 | a网在线 | 国产wwww | 国产中文99视频在线观看 | 中国免费黄色 | 香蕉成人在线视频 | 国产精品视频在线免费观看 | 色播视频网站 | 免费男女乱淫真视频 | 在线视频a | 欧美中文字幕一区二区三区亚洲 | 免费a网 | 色婷婷a v| 天天色综合6 |