第十三周周总结

2020.05.16

本周完成了视频中截取帧图篇,并识别图片中车牌号的功能。

识别基本思路:先是车牌提取,识别图中车牌位置并保存车牌图片(流程:高斯去噪、灰度处理、sobel边缘检测、自适应阈值处理、闭运算、中值滤波去除噪点、轮廓绘制、遍历所有轮廓,去除车牌(车牌 宽>2倍高、为了识别准确,只识别靠近摄像头的车牌号,远处车牌号太不清楚,选择y>500,x<1250、轮廓宽<100 并且>50))

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
# 导入所需模块
import cv2
from matplotlib import pyplot as plt
 
 
def cp_tiqu(name):
    # 加载图片
    rawImage = cv2.imread(name)
    # plt_show0('yuantu',rawImage)
 
    # 高斯去噪
    image = cv2.GaussianBlur(rawImage, (3, 3), 0)
    # 预览效果
    # plt_show0('GaussianBlur',image)
    # 灰度处理
    gray_image = cv2.cvtColor(image, cv2.COLOR_RGB2GRAY)
    plt_show('COLOR_RGB2GRAY', gray_image)
 
    # sobel算子边缘检测(做了一个y方向的检测)
    Sobel_x = cv2.Sobel(gray_image, cv2.CV_16S, 1, 0)
    # Sobel_y = cv2.Sobel(image, cv2.CV_16S, 0, 1)
    absX = cv2.convertScaleAbs(Sobel_x)  # 转回uint8
    # absY = cv2.convertScaleAbs(Sobel_y)
    # dst = cv2.addWeighted(absX, 0.5, absY, 0.5, 0)
    image = absX
    plt_show('Sobel bianyuan', image)
 
    # 自适应阈值处理
    ret, image = cv2.threshold(image, 0, 255, cv2.THRESH_OTSU)
    plt_show('threshold yuzhi', image)
 
    # 闭运算,是白色部分练成整体
    kernelX = cv2.getStructuringElement(cv2.MORPH_RECT, (3, 3))
    print(kernelX)
    image = cv2.morphologyEx(image, cv2.MORPH_CLOSE, kernelX, iterations=2)
    plt_show('biyunsuan', image)
    # 去除一些小的白点
    kernelX = cv2.getStructuringElement(cv2.MORPH_RECT, (20, 1))
    kernelY = cv2.getStructuringElement(cv2.MORPH_RECT, (1, 19))
    '''
 
 
    # 膨胀,腐蚀
    image = cv2.dilate(image, kernelX)
    image = cv2.erode(image, kernelX)
    # 腐蚀,膨胀
    image = cv2.erode(image, kernelY)
    image = cv2.dilate(image, kernelY)
 
    plt_show('pengzhangfushi',image)
    '''
    # 中值滤波去除噪点
    image = cv2.medianBlur(image, 15)
    plt_show('chu zao', image)
 
    # 轮廓检测
    # cv2.RETR_EXTERNAL表示只检测外轮廓
    # cv2.CHAIN_APPROX_SIMPLE压缩水平方向,垂直方向,对角线方向的元素,只保留该方向的终点坐标,例如一个矩形轮廓只需4个点来保存轮廓信息
    contours, hierarchy = cv2.findContours(image, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)
    # 绘制轮廓
    image1 = rawImage.copy()
    cv2.drawContours(image1, contours, -1, (0, 255, 0), 5)
    plt_show0('lunkuo', image1)
 
    # 筛选出车牌位置的轮廓
    # 这里我只做了一个车牌的长宽比在3:1到4:1之间这样一个判断
    num = 1
    for item in contours:
 
        # cv2.boundingRect用一个最小的矩形,把找到的形状包起来
        rect = cv2.boundingRect(item)
        x = rect[0]
        y = rect[1]
        weight = rect[2]
        height = rect[3]
        # 440mm×140mm
        # if (weight > (height * 3)) and (weight < (height * 4)) and y > 500:
        if (weight > (height * 2)) and y > 500 and x < 1250 and weight < 100 and weight > 50:
            image = rawImage[y:y + height, x:x + weight]
            #         cv_show('image',image)
            # 图像保存
 
            image_name = 'car' + str(num) + '.jpg'
            print(image_name)
            plt_show0('save', image)
            cv2.imwrite(image_name, image)
            num += 1
 
if __name__ == '__main__':
 
    cp_tiqu("120.jpg")

  原图:

 

 获取车牌图片信息:

 

 

 

 

第二步:将车牌图篇分割为一个个字符图片

思路:高斯去噪、灰度处理、自适应阈值、计算二值、轮廓绘制、筛选各个字符位置的轮廓

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
# 导入所需模块
import cv2
from matplotlib import pyplot as plt
 
def zifu_tiqu(name):
    # 加载图片
    rawImage = cv2.imread(name)
    plt_show0('yuantu', rawImage)
 
    # 高斯去噪
    image = cv2.GaussianBlur(rawImage, (3, 3), 0)
    # 预览效果
    plt_show0('GaussianBlur', image)
 
    # 灰度处理
    gray_image = cv2.cvtColor(image, cv2.COLOR_RGB2GRAY)
    plt_show('gray image', gray_image)
 
    # 自适应阈值处理
    ret, image = cv2.threshold(gray_image, 0, 255, cv2.THRESH_OTSU)
    plt_show('yuzhi', image)
 
    # 计算二值图像黑白点的个数,处理绿牌照问题,让车牌号码始终为白色
    area_white = 0
    area_black = 0
    height, width = image.shape
    print(image.shape)
    for i in range(height):
        for j in range(width):
            if image[i, j] == 255:
                area_white += 1
            else:
                area_black += 1
    #if area_white > area_black:
       # ret, image = cv2.threshold(gray_image, 0, 255, cv2.THRESH_OTSU | cv2.THRESH_BINARY_INV)
        #plt_show('erzhi', image)
 
    kernel = cv2.getStructuringElement(cv2.MORPH_RECT, (1, 1))
   contours, hierarchy = cv2.findContours(image, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)
    # 绘制轮廓
    image1 = rawImage.copy()
    cv2.drawContours(image1, contours, -1, (0, 255, 0), 1)
    plt_show0('lun kuo', image1)
 
    # 筛选出各个字符的位置的轮廓
    words = []
    for item in contours:
        # cv2.boundingRect用一个最小的矩形,把找到的形状包起来
        word = []
        rect = cv2.boundingRect(item)
        x = rect[0]
        y = rect[1]
        weight = rect[2]
        height = rect[3]
        word.append(x)
        word.append(y)
        word.append(weight)
        word.append(height)
        words.append(word)
 
    words = sorted(words, key=lambda s: s[0], reverse=False)
 
    print(words)
    i = 0
    for word in words:
        if (word[3] > (word[2])) and (word[3] < (word[2] * 5)):
            i = i + 1
            image = rawImage[word[1]:word[1] + word[3], word[0]:word[0] + word[2]]
            plt_show0('single', image)
            print('test2_' + str(i) + '.jpg')
            cv2.imwrite('chepai/test2_' + str(i) + '.jpg', image

  

posted @   HHHarden13  阅读(171)  评论(0编辑  收藏  举报
编辑推荐:
· DeepSeek 解答了困扰我五年的技术问题
· 为什么说在企业级应用开发中,后端往往是效率杀手?
· 用 C# 插值字符串处理器写一个 sscanf
· Java 中堆内存和栈内存上的数据分布和特点
· 开发中对象命名的一点思考
阅读排行:
· PPT革命!DeepSeek+Kimi=N小时工作5分钟完成?
· What?废柴, 还在本地部署DeepSeek吗?Are you kidding?
· DeepSeek企业级部署实战指南:从服务器选型到Dify私有化落地
· 程序员转型AI:行业分析
· 重磅发布!DeepSeek 微调秘籍揭秘,一键解锁升级版全家桶,AI 玩家必备神器!
点击右上角即可分享
微信分享提示