訂閱
糾錯(cuò)
加入自媒體

一文了解如何使用OpenCV進(jìn)行圖像處理

介紹

OpenCV – 開源計(jì)算機(jī)視覺。它是計(jì)算機(jī)視覺和圖像處理任務(wù)中使用最廣泛的工具之一。它被用于各種應(yīng)用,如面部檢測(cè)、視頻捕捉、跟蹤移動(dòng)物體、對(duì)象公開。如今應(yīng)用在 Covid 中,如口罩檢測(cè)、社交距離等等。

在這篇博客中,將通過實(shí)際示例涵蓋圖像處理中一些最重要的任務(wù)來詳細(xì)介紹 OpenCV。那么讓我們開始吧

目錄

邊緣檢測(cè)和圖像梯度

圖像的膨脹、打開、關(guān)閉和腐蝕

透視變換

圖像金字塔

裁剪

縮放、插值和重新調(diào)整大小

閾值、自適應(yīng)閾值和二值化

銳化

模糊

輪廓

使用霍夫線檢測(cè)線

尋找角落

計(jì)算圓和橢圓

邊緣檢測(cè)和圖像梯度

它是圖像處理中最基本和最重要的技術(shù)之一。檢查以下代碼以獲取完整實(shí)現(xiàn)。

image = cv2.imread('fruit.jpg')
image = cv2.cvtColor(image, cv2.COLOR_BGR2RGB)
hgt, wdt,_ = image.shape
# Sobel Edges
x_sobel = cv2.Sobel(image, cv2.CV_64F, 0, 1, ksize=5)
y_sobel = cv2.Sobel(image, cv2.CV_64F, 1, 0, ksize=5)
plt.figure(figsize=(20, 20))
plt.subplot(3, 2, 1)
plt.title("Original")
plt.imshow(image)
plt.subplot(3, 2, 2)
plt.title("Sobel X")
plt.imshow(x_sobel)
plt.subplot(3, 2, 3)
plt.title("Sobel Y")
plt.imshow(y_sobel)
sobel_or = cv2.bitwise_or(x_sobel, y_sobel)
plt.subplot(3, 2, 4)
plt.imshow(sobel_or)
laplacian = cv2.Laplacian(image, cv2.CV_64F)
plt.subplot(3, 2, 5)
plt.title("Laplacian")
plt.imshow(laplacian)
## There are two values: threshold1 and threshold2.
## Those gradients that are greater than threshold2 => considered as an edge
## Those gradients that are below threshold1 => considered not to be an edge.
## Those gradients Values that are in between threshold1 and threshold2 => either classi?ed as edges or non-edges
# The first threshold gradient
canny = cv2.Canny(image, 50, 120)
plt.subplot(3, 2, 6)
plt.imshow(canny)

圖像的膨脹、打開、關(guān)閉和腐蝕

這是基本的圖像處理操作。這些用于去除噪聲、查找圖像中的強(qiáng)度洞或凹凸等等。檢查以下代碼以獲得實(shí)際實(shí)現(xiàn)。image = cv2.imread('LinuxLogo.jpg')
image = cv2.cvtColor(image, cv2.COLOR_BGR2RGB)
plt.figure(figsize=(20, 20))
plt.subplot(3, 2, 1)
plt.title("Original")
plt.imshow(image)
kernel = np.ones((5,5), np.uint8)
erosion = cv2.erode(image, kernel, iterations = 1)
plt.subplot(3, 2, 2)
plt.title("Erosion")
plt.imshow(erosion)
dilation = cv2.dilate(image, kernel, iterations = 1)
plt.subplot(3, 2, 3)
plt.title("Dilation")
plt.imshow(dilation)
opening = cv2.morphologyEx(image, cv2.MORPH_OPEN, kernel)
plt.subplot(3, 2, 4)
plt.title("Opening")
plt.imshow(opening)
closing = cv2.morphologyEx(image, cv2.MORPH_CLOSE, kernel)
plt.subplot(3, 2, 5)
plt.title("Closing")
plt.imshow(closing)

透視變換為了獲得更好的圖像信息,我們可以改變視頻或圖像的視角。在這個(gè)轉(zhuǎn)換中,我們需要通過改變視角來提供圖像上我們想要獲取信息的點(diǎn)。在 OpenCV 中,我們使用兩個(gè)函數(shù)進(jìn)行透視變換getPerspectiveTransform()和warpPerspective()。檢查以下代碼以獲取完整實(shí)現(xiàn)。

image = cv2.imread('scan.jpg')
image = cv2.cvtColor(image, cv2.COLOR_BGR2RGB)
plt.figure(figsize=(20, 20))
plt.subplot(1, 2, 1)
plt.title("Original")
plt.imshow(image)
points_A = np.float32([[320,15], [700,215], [85,610], [530,780]])
points_B = np.float32([[0,0], [420,0], [0,594], [420,594]])
M = cv2.getPerspectiveTransform(points_A, points_B)
warped = cv2.warpPerspective(image, M, (420,594))
plt.subplot(1, 2, 2)
plt.title("warpPerspective")
plt.imshow(warped)

圖像金字塔

當(dāng)我們需要縮放對(duì)象檢測(cè)時(shí),這是一項(xiàng)非常有用的技術(shù)。OpenCV 使用兩種常見的圖像金字塔:高斯金字塔和拉普拉斯金字塔。使用OpenCV 中的pyrUp()和pyrDown()函數(shù)對(duì)圖像進(jìn)行下采樣或上采樣。檢查以下代碼以獲得實(shí)際實(shí)現(xiàn)。

image = cv2.imread('butterfly.jpg')
image = cv2.cvtColor(image, cv2.COLOR_BGR2RGB)
plt.figure(figsize=(20, 20))
plt.subplot(2, 2, 1)
plt.title("Original")
plt.imshow(image)
smaller = cv2.pyrDown(image)
larger = cv2.pyrUp(smaller)
plt.subplot(2, 2, 2)
plt.title("Smaller")
plt.imshow(smaller)
plt.subplot(2, 2, 3)
plt.title("Larger")
plt.imshow(larger)

裁剪它是圖像處理中最重要和最基本的技術(shù)之一,裁剪用于獲取圖像的特定部分。裁剪圖像。你只需要根據(jù)你感興趣的區(qū)域從圖像中獲取坐標(biāo)。如需完整分析,請(qǐng)查看 OpenCV 中的以下代碼。

image = cv2.imread('messi.jpg')
image = cv2.cvtColor(image, cv2.COLOR_BGR2RGB)
plt.figure(
Aigsize=(20, 20))
plt.subplot(2, 2, 1)
plt.title("Original")
plt.imshow(image)
hgt, wdt = image.shape[:2]
start_row, start_col = int(hgt * .25), int(wdt * .25)
end_row, end_col = int(height * .75), int(width * .75)
cropped = image[start_row:end_row , start_col:end_col]
plt.subplot(2, 2, 2)
plt.imshow(cropped)

縮放、插值和重新調(diào)整大小

調(diào)整大小是 OpenCV 中最簡(jiǎn)單的任務(wù)之一。它提供了一個(gè)resize()函數(shù),它接受圖像、輸出大小圖像、插值、x 比例和 y 比例等參數(shù)。檢查以下代碼以獲取完整實(shí)現(xiàn)。image = cv2.imread('/kaggle/input/opencv-samples-images/data/fruits.jpg')
image = cv2.cvtColor(image, cv2.COLOR_BGR2RGB)
plt.figure(figsize=(20, 20))
plt.subplot(2, 2, 1)
plt.title("Original")
plt.imshow(image)
image_scaled = cv2.resize(image, None, fx=0.75, fy=0.75)
plt.subplot(2, 2, 2)
plt.title("Scaling - Linear Interpolation")
plt.imshow(image_scaled)
img_scaled = cv2.resize(image, None, fx=2, fy=2, interpolation = cv2.INTER_CUBIC)
plt.subplot(2, 2, 3)
plt.title("Scaling - Cubic Interpolation")
plt.imshow(img_scaled)
img_scaled = cv2.resize(image, (900, 400), interpolation = cv2.INTER_AREA)
plt.subplot(2, 2, 4)
plt.title("Scaling - Skewed Size")
plt.imshow(img_scaled)

閾值、自適應(yīng)閾值和二值化檢查以下代碼以獲取完整實(shí)現(xiàn)。

# Load our new image
image = cv2.imread('Origin_of_Species.jpg', 0)
plt.figure(figsize=(30, 30))
plt.subplot(3, 2, 1)
plt.title("Original")
plt.imshow(image)
ret,thresh1 = cv2.threshold(image, 127, 255, cv2.THRESH_BINARY)
plt.subplot(3, 2, 2)
plt.title("Threshold Binary")
plt.imshow(thresh1)
image = cv2.GaussianBlur(image, (3, 3), 0)
thresh = cv2.a(chǎn)daptiveThreshold(image, 255, cv2.ADAPTIVE_THRESH_MEAN_C, cv2.THRESH_BINARY, 3, 5)
plt.subplot(3, 2, 3)
plt.title("Adaptive Mean Thresholding")
plt.imshow(thresh)
_, th2 = cv2.threshold(image, 0, 255, cv2.THRESH_BINARY + cv2.THRESH_OTSU)
plt.subplot(3, 2, 4)
plt.title("Otsu's Thresholding")
plt.imshow(th2)
plt.subplot(3, 2, 5)
blur = cv2.GaussianBlur(image, (5,5), 0)
_, th3 = cv2.threshold(blur, 0, 255, cv2.THRESH_BINARY + cv2.THRESH_OTSU)
plt.title("Guassian Otsu's Thresholding")
plt.imshow(th3)
plt.show()

銳化檢查以下代碼以使用 OpenCV 銳化圖像。

image = cv2.imread('building.jpg')

image = cv2.cvtColor(image, cv2.COLOR_BGR2RGB)
plt.figure(figsize=(20, 20))
plt.subplot(1, 2, 1)
plt.title("Original")
plt.imshow(image)
kernel_sharpening = np.a(chǎn)rray([[-1,-1,-1],
                             [-1,9,-1],
                             [-1,-1,-1]])
sharpened = cv2.filter2D(image, -1, kernel_sharpening)
plt.subplot(1, 2, 2)
plt.title("Image Sharpening")
plt.imshow(sharpened)
plt.show()

模糊檢查以下代碼以使用 OpenCV 模糊圖像。

image = cv2.imread('home.jpg')

image = cv2.cvtColor(image, cv2.COLOR_BGR2RGB)
plt.figure(figsize=(20, 20))
plt.subplot(2, 2, 1)
plt.title("Original")
plt.imshow(image)
kernel_3x3 = np.ones((3, 3), np.float32) / 9
blurred = cv2.filter2D(image, -1, kernel_3x3)
plt.subplot(2, 2, 2)
plt.title("3x3 Kernel Blurring")
plt.imshow(blurred)
kernel_7x7 = np.ones((7, 7), np.float32) / 49
blurred2 = cv2.filter2D(image, -1, kernel_7x7)
plt.subplot(2, 2, 3)
plt.title("7x7 Kernel Blurring")
plt.imshow(blurred2)

輪廓圖像輪廓——這是一種識(shí)別圖像中對(duì)象結(jié)構(gòu)輪廓的方法。有助于識(shí)別物體的形狀。OpenCV 提供了一個(gè)findContours函數(shù),你需要在其中傳遞 canny 邊緣作為參數(shù)。檢查以下代碼以獲取完整實(shí)現(xiàn)。

# Load the data
image = cv2.imread('pic.png')
image = cv2.cvtColor(image, cv2.COLOR_BGR2RGB)
plt.figure(figsize=(20, 20))
plt.subplot(2, 2, 1)
plt.title("Original")
plt.imshow(image)
# Grayscale
gray = cv2.cvtColor(image,cv2.COLOR_BGR2GRAY)
# Canny edges
edged = cv2.Canny(gray, 30, 200)
plt.subplot(2, 2, 2)
plt.title("Canny Edges")
plt.imshow(edged)
# Finding Contours
contour, hier = cv2.findContours(edged, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_NONE)
plt.subplot(2, 2, 3)
plt.imshow(edged)
print("Count of Contours  = " + str(len(contour)))
# All contours
cv2.drawContours(image, contours, -1, (0,255,0), 3)
plt.subplot(2, 2, 4)
plt.title("Contours")
plt.imshow(image)

使用霍夫線檢測(cè)線可以使用霍夫線檢測(cè)圖像中的線條。OpenCV 提供了一個(gè)HouhLines 函數(shù),你必須在其中傳遞閾值。閾值是將其視為一條線的最低投票數(shù)。有關(guān)詳細(xì)概述,請(qǐng)查看以下代碼中,利用OpenCV中的HoughLines() 實(shí)現(xiàn)直線檢測(cè)。

# Load the image
image = cv2.imread('sudoku.png')
image = cv2.cvtColor(image, cv2.COLOR_BGR2RGB)
plt.figure(figsize=(20, 20))
# Grayscale
gray = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)
# Canny Edges
edges = cv2.Canny(gray, 100, 170, apertureSize = 3)
plt.subplot(2, 2, 1)
plt.title("edges")
plt.imshow(edges)
# Run HoughLines Fucntion
lines = cv2.HoughLines(edges, 1, np.pi/180, 200)
# Run for loop through each line
for line in lines:
   rho, theta = line[0]
   a = np.cos(theta)
   b = np.sin(theta)
   x0 = a * rho
   y0 = b * rho
   x_1 = int(x0 + 1000 * (-b))
   y_1 = int(y0 + 1000 * (a))
   x_2 = int(x0 - 1000 * (-b))
   y_2 = int(y0 - 1000 * (a))
   cv2.line(image, (x_1, y_1), (x_2, y_2), (255, 0, 0), 2)
# Show Final output
plt.subplot(2, 2, 2)
plt.imshow(image)

尋找角落要找到圖像的角點(diǎn),請(qǐng)使用OpenCV 中的cornerHarris 函數(shù)。有關(guān)詳細(xì)概述,請(qǐng)查看以下代碼,獲取使用 OpenCV 查找角點(diǎn)的完整實(shí)現(xiàn)。

# Load image
image = cv2.imread('chessboard.png')
# Grayscaling
image = cv2.cvtColor(image, cv2.COLOR_BGR2RGB)
plt.figure(figsize=(10, 10))
gray = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)
# CornerHarris function  want input to be float
gray = np.float32(gray)
h_corners = cv2.cornerHarris(gray, 3, 3, 0.05)
kernel = np.ones((7,7),np.uint8)
h_corners = cv2.dilate(harris_corners, kernel, iterations = 10)
image[h_corners > 0.024 * h_corners.max() ] = [256, 128, 128]
plt.subplot(1, 1, 1)
# Final Output
plt.imshow(image)

計(jì)算圓和橢圓要計(jì)算 圖像中的圓和橢圓,請(qǐng)使用OpenCV 中的SimpleBlobDetector 函數(shù)。有關(guān)詳細(xì)概述,請(qǐng)查看以下代碼,以獲取 使用 OpenCV 計(jì)算圖像中的圓和橢圓的完整實(shí)現(xiàn)。

# Load image
image = cv2.imread('blobs.jpg')
image = cv2.cvtColor(image, cv2.COLOR_BGR2RGB)
plt.figure(figsize=(20, 20))
detector = cv2.SimpleBlobDetector_create()
# Detect blobs
points = detector.detect(image)
blank = np.zeros((1,1))
blobs = cv2.drawKeypoints(image, points, blank, (0,0,255),
                                     cv2.DRAW_MATCHES_FLAGS_DRAW_RICH_KEYPOINTS)
number_of_blobs = len(keypoints)
text = "Total Blobs: " + str(len(keypoints))
cv2.putText(blobs, text, (20, 550), cv2.FONT_HERSHEY_SIMPLEX, 1, (100, 0, 255), 2)
plt.subplot(2, 2, 1)
plt.imshow(blobs)
# Filtering parameters
# Initialize parameter settiing using cv2.SimpleBlobDetector
params = cv2.SimpleBlobDetector_Params()
# Area filtering parameters
params.filterByArea = True
params.minArea = 100
# Circularity filtering parameters
params.filterByCircularity = True
params.minCircularity = 0.9
# Convexity filtering parameters
params.filterByConvexity = False
params.minConvexity = 0.2
#  inertia filtering parameters
params.filterByInertia = True
params.minInertiaRatio = 0.01
# detector with the parameters
detector = cv2.SimpleBlobDetector_create(params)
# Detect blobs
keypoints = detector.detect(image)
# Draw blobs on our image as red circles
blank = np.zeros((1,1))
blobs = cv2.drawKeypoints(image, keypoints, blank, (0,255,0),
                                     cv2.DRAW_MATCHES_FLAGS_DRAW_RICH_KEYPOINTS)
number_of_blobs = len(keypoints)
text = "No.  Circular Blobs: " + str(len(keypoints))
cv2.putText(blobs, text, (20, 550), cv2.FONT_HERSHEY_SIMPLEX, 1, (0, 100, 255), 2)
# Show blobs
plt.subplot(2, 2, 2)
plt.title("Filtering Circular Blobs Only")
plt.imshow(blobs)

尾注

因此,在本文中,我們?cè)敿?xì)討論了使用 OpenCV進(jìn)行圖像處理。希望你能從這個(gè)博客中學(xué)到一些東西,它會(huì)在未來對(duì)你有所幫助。感謝你的耐心閱讀。祝你好運(yùn)!

聲明: 本文由入駐維科號(hào)的作者撰寫,觀點(diǎn)僅代表作者本人,不代表OFweek立場(chǎng)。如有侵權(quán)或其他問題,請(qǐng)聯(lián)系舉報(bào)。

發(fā)表評(píng)論

0條評(píng)論,0人參與

請(qǐng)輸入評(píng)論內(nèi)容...

請(qǐng)輸入評(píng)論/評(píng)論長(zhǎng)度6~500個(gè)字

您提交的評(píng)論過于頻繁,請(qǐng)輸入驗(yàn)證碼繼續(xù)

  • 看不清,點(diǎn)擊換一張  刷新

暫無評(píng)論

暫無評(píng)論

    人工智能 獵頭職位 更多
    掃碼關(guān)注公眾號(hào)
    OFweek人工智能網(wǎng)
    獲取更多精彩內(nèi)容
    文章糾錯(cuò)
    x
    *文字標(biāo)題:
    *糾錯(cuò)內(nèi)容:
    聯(lián)系郵箱:
    *驗(yàn) 證 碼:

    粵公網(wǎng)安備 44030502002758號(hào)