opencv銀行卡號識別的項目實踐
OpenCV(Open Source Computer Vision Library)是一個開源的計算機視覺庫,主要用于圖像和視頻處理、目標檢測、特征提取、3D重建以及機器學習任務。它支持多種編程語言(如C++、Python),提供豐富的算法和工具,可用于人臉識別、物體檢測、運動跟蹤、圖像增強等應用,廣泛應用于工業(yè)檢測、自動駕駛、安防監(jiān)控、醫(yī)療影像等領域。其高效性和跨平臺特性使其成為計算機視覺開發(fā)的核心工具之一。在日常生活中,我們可以通過opencv來識別銀行卡卡號,實現(xiàn)銀行卡的分類。
以下是我們用來識別檢測的銀行卡圖片

以及用于模板處理的模板圖片

以下是代碼實現(xiàn)
import numpy as np
import argparse
import cv2
import myutils
#設置參數(shù)
ap=argparse.ArgumentParser()
ap.add_argument('-i','--image',required=True,help='path to iuput image')
ap.add_argument('-t','--template',required=True,help='path to template OCR-A image')
#vars(ap.parse_args()):解析命令行參數(shù)并將其轉(zhuǎn)換為字典形式
args=vars(ap.parse_args())
FIRST_NUMBER={
'3':'American',
'4':'Visa',
'5':'MasterCard',
'6':'Discover'
}
def cv_show(name,image):
cv2.imshow(name,image)
cv2.waitKey(0)
a=args['template']
'''--------模板圖像中數(shù)字的定位處理-----------'''
img=cv2.imread(args['template'])
cv_show('img',img)
ref=cv2.cvtColor(img,cv2.COLOR_BGR2GRAY)
cv_show('ref',ref)
#cv2.threshold():對灰度圖像進行閾值處理,將其轉(zhuǎn)換為二值圖像,cv2.THRESH_BINARY_INV 表示反二進制閾值。
ref=cv2.threshold(ref,10,255,cv2.THRESH_BINARY_INV)[1]
cv_show('ref',ref)
#查找并排序模板圖像中的輪廓
_,refCnts,hierarchy=cv2.findContours(ref,cv2.RETR_EXTERNAL,cv2.CHAIN_APPROX_SIMPLE)
cv2.drawContours(img,refCnts,-1,(0,255,0),3)
cv_show('img',img)
#myutils.sort_contours():對輪廓進行從左到右的排序。
refCnts=myutils.sort_contours(refCnts,method='left-to-right')[0]
digits={}
#遍歷排序后的輪廓,提取每個數(shù)字的 ROI(感興趣區(qū)域),并將其調(diào)整為固定大?。?7x88),存儲在字典 digits 中,鍵為數(shù)字的索引。
#enumerate() 是 Python 中的一個內(nèi)置函數(shù)
# 它的作用是 為可迭代對象添加索引,使得在遍歷時可以同時訪問索引和元素。
for (i,c) in enumerate(refCnts):
(x,y,w,h)=cv2.boundingRect(c)
roi=ref[y:y+h,x:x+w]
roi=cv2.resize(roi,(57, 88))
cv_show('ro',roi)
digits[i]=roi
print(digits)
'''----------信用卡的圖像處理---------------------'''
#信用卡信息處理
image=cv2.imread(args['image'])
image=myutils.resize(image,width=300)
cv_show('image',image)
gray=cv2.cvtColor(image,cv2.COLOR_BGR2GRAY)
cv_show('gray',gray)
#初始化卷積核
rectKernel=cv2.getStructuringElement(cv2.MORPH_RECT,(9,3))
sqKernel=cv2.getStructuringElement(cv2.MORPH_RECT,(5,5))
#頂帽操作
tophat=cv2.morphologyEx(gray,cv2.MORPH_TOPHAT,rectKernel)
cv_show('tophat',tophat)
#-----找到數(shù)字邊框---------
# 1、通過閉操作(先膨脹,再腐蝕)將數(shù)字連在一起
closeX=cv2.morphologyEx(tophat,cv2.MORPH_CLOSE,rectKernel)
cv_show('closeX',closeX)
#THRESH_OTSU會自動尋找到合適的閾值,適合雙峰,需要把閾值參數(shù)設置為0
thresh=cv2.threshold(closeX,0,255,cv2.THRESH_BINARY | cv2.THRESH_OTSU)[1]
cv_show('thresh',thresh)
# 再來一個閉操作
# thresh1=cv2.morphologyEx(thresh,cv2.MORPH_CLOSE,sqKernel)
# cv_show('thresh1',thresh1)
#計算輪廓
_,threshCnts,h=cv2.findContours(thresh.copy(),cv2.RETR_EXTERNAL,cv2.CHAIN_APPROX_SIMPLE)
cnts=threshCnts
cur_img=image.copy()
cv2.drawContours(cur_img,cnts,-1,(0,255,0),3)
cv_show('cur_img',cur_img)
#遍歷輪廓,找到數(shù)字部分像素區(qū)域
locs=[]
for (i,c) in enumerate(cnts):
(x,y,w,h)=cv2.boundingRect(c)#計算外接矩形
ar=w/float(h)
#選擇合適區(qū)域
if ar>2.5 and ar<4.0:
if (w>40 and w<55) and (h>10 and h<20):
locs.append((x,y,w,h))
#將輪廓從左到右排序
locs=sorted(locs,key=lambda x:x[0])
output=[]
for (i,(gX,gY,gW,gH)) in enumerate(locs):
groupOutput=[]
group=gray[gY-5:gY+gH+5,gX-5:gX+gW+5]
cv_show('group',group)
group=cv2.threshold(group,0,255,cv2.THRESH_BINARY | cv2.THRESH_OTSU)[1]
cv_show('group',group)
group_,digitCnts,hierarchy=cv2.findContours(group.copy(),cv2.RETR_EXTERNAL,cv2.CHAIN_APPROX_SIMPLE)
digitCnts=myutils.sort_contours(digitCnts,method='left-to-right')[0]
for c in digitCnts:
(x,y,w,h)=cv2.boundingRect(c)
roi=group[y:y+h,x:x+w]
roi=cv2.resize(roi,(57,88))
cv_show('roi',roi)
#使用模塊匹配,計算匹配得分
scores=[]
##在模板中計算每一個得分
#digits 是一個字典
#digits.items() 方法會返回一個包含字典中所有鍵值對的可迭代對象,其中每個元素是一個元組,元組的第一個元素是鍵,第二個元素是對應的值。
for (digit,digitROI) in digits.items():
## 模板匹配
#cv2.matchTemplate此函數(shù)用于在一幅圖像里查找與給定模板最匹配的區(qū)域
# roi:代表輸入圖像,也就是要在其中查找模板的圖像。
# digitROI:代表模板圖像,也就是你想要在輸入圖像中查找的部分。
# cv2.TM_CCOEFF:表示匹配方法,這里采用的是相關性系數(shù)匹配法。
#函數(shù)會返回一個二維的 NumPy 數(shù)組
result=cv2.matchTemplate(roi,digitROI,cv2.TM_CCOEFF)
#cv2.minMaxLoc 函數(shù)用于在一個單通道的矩陣(通常是圖像或模板匹配結果)中查找最小值、最大值以及它們對應的位置。
#該函數(shù)返回一個包含四個值的元組,依次為:
# 矩陣中的最小值。
# 矩陣中的最大值。
# 最小值所在的位置(以元組 (x, y) 形式表示)。
# 最大值所在的位置(以元組 (x, y) 形式表示)
(_,score,_,_)=cv2.minMaxLoc(result)
scores.append(score)
#np.argmax 用于返回數(shù)組中最大值所在的索引。
#例如,如果 scores = [1, 5, 3],那么 np.argmax(scores) 會返回 1,
#str 是 Python 內(nèi)置函數(shù),用于將一個對象轉(zhuǎn)換為字符串類型。
groupOutput.append(str(np.argmax(scores)))
# 畫出來
cv2.rectangle(image,(gX-5,gY-5),(gX+gW+5,gY+gH+5),(0,0,255),1)
# cv2.putText()是OpenCV庫中的一個函數(shù),用于在圖像上添加文本。
cv2.putText(image,''.join(groupOutput),(gX,gY-15),cv2.FONT_HERSHEY_SIMPLEX,0.65,(0,0,255),2)
output.extend(groupOutput)
print('Credit Card Type:{}'.format(FIRST_NUMBER[output[0]]))
print('Credit Card#:{}'.format(''.join(output)))
cv2.imshow('image',image)
cv2.waitKey(0)打印輸出結果如下圖所示


到此這篇關于opencv銀行卡號識別的項目實踐的文章就介紹到這了,更多相關opencv銀行卡號識別內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關文章希望大家以后多多支持腳本之家!
相關文章
Python實現(xiàn)希爾伯特變換(Hilbert transform)的示例代碼
希爾伯特變換(Hilbert transform)是一個對函數(shù)產(chǎn)生定義域相同的函數(shù)的線性算子,而且希爾伯特變換在信號處理中很重要,所以本文和大家分享了Python實現(xiàn)希爾伯特變換的代碼,需要的可以參考一下2023-04-04

