OpenCV实践项目之银行卡卡号识别功能
项目简介
本项目利用OpenCV实现银行卡卡号的自动识别功能,能够对输入的照片或摄像头视频进行实时的卡号识别,并且将识别结果呈现在界面上,方便用户进行后续操作。
项目流程
以下是本项目的主要流程:
- 图像预处理
- 字符分割
- 字符识别
- 结果呈现
下面将对每个流程进行详细的说明。
图像预处理
图像预处理是整个卡号识别过程中的关键步骤。主要任务是对输入的银行卡图像进行处理,以便后续的字符分割和字符识别操作可以顺利进行。
具体实现方式通常包括以下几个步骤:
- 转为灰度图像
- 图像二值化
- 去除噪声
- 边缘检测
示例代码如下:
import cv2
# 加载输入图像
image = cv2.imread("input.jpg")
# 转为灰度图像
gray = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)
# 图像二值化
threshold = 100
ret, binary = cv2.threshold(gray, threshold, 255, cv2.THRESH_BINARY)
# 去除噪声
kernel = cv2.getStructuringElement(cv2.MORPH_RECT, (3, 3))
morphology = cv2.morphologyEx(binary, cv2.MORPH_CLOSE, kernel)
# 边缘检测
canny = cv2.Canny(morphology, 40, 150)
# 显示预处理后的图像
cv2.imshow("Preprocessed", canny)
cv2.waitKey(0)
cv2.destroyAllWindows()
字符分割
字符分割是将预处理后的银行卡图像中的字符分离出来的过程。由于每个字符之间的间隔大小不同,而且银行卡中的字符也存在不同的字体、大小等差异,因此字符分割是整个卡号识别过程中最为困难的一个环节。
传统的字符分割方法通常包括以下几个步骤:
- 水平投影
- 垂直投影
- 按列切割
- 去除多余字符
示例代码如下:
import cv2
# 加载预处理后的图像
image = cv2.imread("preprocessed.jpg")
# 水平投影
horizontal = cv2.reduce(image, 1, cv2.REDUCE_AVG)
horizontal = cv2.threshold(horizontal, 250, 255, cv2.THRESH_BINARY)[1]
# 垂直投影
vertical = cv2.reduce(image, 0, cv2.REDUCE_AVG)
vertical = cv2.threshold(vertical, 250, 255, cv2.THRESH_BINARY)[1]
# 按列切割
width = len(image[0])
height = len(image)
split_lines = []
for i in range(width):
if vertical[0, i] == 0:
continue
start = max(0, i-1)
end = min(width-1, i+1)
for j in range(1, height):
if vertical[j, i] != 0 and vertical[j-1, i] == 0:
split_lines.append((start, i, end, j-1))
break
if j == height - 1 and vertical[j, i] != 0:
split_lines.append((start, i, end, j))
break
# 去除多余字符
split_images = []
for line in split_lines:
if line[3] - line[1] > 10 and line[2] - line[0] > 3:
roi = image[line[1]:line[3], line[0]:line[2]]
split_images.append(roi)
# 显示分割后的字符图像
for i, split_image in enumerate(split_images):
cv2.imshow(f"Split {i}", split_image)
cv2.waitKey(0)
cv2.destroyAllWindows()
字符识别
字符识别是整个卡号识别过程中的最后一步,任务是将分离出来的字符进行识别,输出卡号字符串。
常用的字符识别方法包括基于传统图像处理方法的模板匹配、基于机器学习的卷积神经网络等方法。本项目中使用了一种先进的字符识别算法——深度学习中的卷积神经网络(Convolutional Neural Networks,简称CNN)。
示例代码如下:
import cv2
import numpy as np
from tensorflow.keras.models import load_model
# 加载分割后的字符图像
split_images = []
for i in range(16):
split_image = cv2.imread(f"split_{i}.jpg")
split_image = cv2.cvtColor(split_image, cv2.COLOR_BGR2GRAY)
split_image = split_image.astype(np.float32) / 255.
split_images.append(split_image)
# 加载字符识别模型
model = load_model("model.h5")
# 对每个字符进行识别
card_number = ""
for split_image in split_images:
preprocessed = cv2.resize(split_image, (32, 32))
preprocessed = preprocessed.reshape((1, 32, 32, 1))
prediction = model.predict(preprocessed, batch_size=1)
card_number += str(np.argmax(prediction))
# 显示识别结果
print("Card number:", card_number)
结果呈现
最后一步是将识别出来的卡号字符串呈现在界面上,方便用户进行后续操作。
示例代码如下:
import cv2
from PIL import ImageFont, ImageDraw, Image
# 加载原始图像
image = cv2.imread("input.jpg")
# 绘制卡号
font = ImageFont.truetype("arial.ttf", 40)
image = cv2.cvtColor(image, cv2.COLOR_BGR2RGB)
image = Image.fromarray(image)
draw = ImageDraw.Draw(image)
draw.text((50, 50), card_number, fill=(255, 0, 0), font=font)
# 显示最终结果
result = cv2.cvtColor(np.array(image), cv2.COLOR_RGB2BGR)
cv2.imshow("Result", result)
cv2.waitKey(0)
cv2.destroyAllWindows()
以上代码片段只是本项目的一个简单示例,实际上还需要进行一些调试和优化。在实际实现过程中,还需要考虑更复杂的情况,例如图片倾斜、模糊等问题的处理。
本站文章如无特殊说明,均为本站原创,如若转载,请注明出处:openCV实践项目之银行卡卡号识别功能 - Python技术站