HyperLPR 高性能中文车牌识别系统分析(十)

2021SC@SDUSC

概述

接下来依旧是对SimpleRecognizePlateByE2E()函数及其内部调用的函数进行分析与总结

本篇是对delectPlateRough()函数、finemappingVertical()函数、recognizeOne()函数的分析与总结

detectPlateRough()函数

    def detectPlateRough(self,image_gray,resize_h = 720,en_scale =1.08 ,top_bottom_padding_rate = 0.05):
        if top_bottom_padding_rate>0.2:
            print("error:top_bottom_padding_rate > 0.2:",top_bottom_padding_rate)
            exit(1)
        height = image_gray.shape[0]
        padding =    int(height*top_bottom_padding_rate)
        scale = image_gray.shape[1]/float(image_gray.shape[0])
        image = cv2.resize(image_gray, (int(scale*resize_h), resize_h))
        image_color_cropped = image[padding:resize_h-padding,0:image_gray.shape[1]]
        image_gray = cv2.cvtColor(image_color_cropped,cv2.COLOR_RGB2GRAY)
        watches = self.watch_cascade.detectMultiScale(image_gray, en_scale, 2, minSize=(36, 9),maxSize=(36*40, 9*40))
        cropped_images = []
        for (x, y, w, h) in watches:
            x -= w * 0.14
            w += w * 0.28
            y -= h * 0.15
            h += h * 0.3
            cropped = self.cropImage(image_color_cropped, (int(x), int(y), int(w), int(h)))
            cropped_images.append([cropped,[x, y+padding, w, h]])
        return cropped_images

首先是进行异常检测,如果top_bottom_padding_rate>0.2,会直接报错并且退出。

接着定义了三个变量。height定义为输入图片的高度,padding定义为图片高度乘top_bottom_padding_rate,显然就是图片上下部分所占实际高度,scale是定义的一个比例系数,即图片的长除以图片的高接着对图片进行了缩放,resize函数用于对图片进行缩放,缩放后高度统一。

对图片进行裁剪,在高度这一维度上,将之前判定为上下边缘的部分裁剪掉,在长度这一维度上不进行裁剪,全部保留。padding是之前根据上下边缘占比乘以图片高度,算出来的上下边缘的实际高度,只选取图片从上边缘padding到下边缘resize_h-padding的部分,剩下的上下边缘予以舍弃。裁剪后的图片命名为image_color_cropped

对图片进行格式转换,将刚才裁剪后的图片转换成灰度图片,这样就可以再用级联分类器进行模式识别。detectMultiScale是cv2中进行模式识别的函数,它能够对输入的图片进行识别,识别出所有待识别模式(在这里是车牌)的位置坐标和大小,将其用矩vector表示并返回,存储在watches。最后一步就是对刚才模式识别出的结果进行处理。watches中存储的x,y,w,h,分别代表识别出的车牌的横坐标、纵坐标、水平宽度、竖直高度。对刚才识别出的每个车牌都进行处理,分别修改它们的横坐标、纵坐标,并扩大它们的宽度和高度,这样就扩大了识别出车牌的边框。最后用cropImage函数对它们进行裁剪,裁剪下来的就是粗识别出的车牌的边框

modelFinemapping()函数

    def model_finemapping(self):
        input = Input(shape=[16, 66, 3])  # change this shape to [None,None,3] to enable arbitraty shape input
        x = Conv2D(10, (3, 3), strides=1, padding='valid', name='conv1')(input)
        x = Activation("relu", name='relu1')(x)
        x = MaxPool2D(pool_size=2)(x)
        x = Conv2D(16, (3, 3), strides=1, padding='valid', name='conv2')(x)
        x = Activation("relu", name='relu2')(x)
        x = Conv2D(32, (3, 3), strides=1, padding='valid', name='conv3')(x)
        x = Activation("relu", name='relu3')(x)
        x = Flatten()(x)
        output = Dense(2,name = "dense")(x)
        output = Activation("relu", name='relu4')(output)
        model = Model([input], [output])
        return model

首先它对输入的图片大小进行了调整,调整成为统一的大小,这样输入图片的大小就可以是任意的接下来的部分,函数整体上就是一个卷积神经网络,它反复调用卷积(Conv2D)、激励(Activation)、池化(MaxPool2D等函数,这说明在程序所建立的卷积神经网络中,卷积、激励和池化层都有多层并且间隔交错分布。处理完成后,最后用flatten函数对矩阵进行降维,转化为数组。

finemappingVertical()函数

 def finemappingVertical(self,image,rect):
        resized = cv2.resize(image,(66,16))
        resized = resized.astype(np.float)/255
        res_raw= self.modelFineMapping.predict(np.array([resized]))[0]
        res  =res_raw*image.shape[1]
        res = res.astype(np.int)
        H,T = res
        H-=3
        if H<0:
            H=0
        T+=2;
        if T>= image.shape[1]-1:
            T= image.shape[1]-1
        rect[2] -=  rect[2]*(1-res_raw[1] + res_raw[0])
        rect[0]+=res[0]
        image = image[:,H:T+2]
        image = cv2.resize(image, (int(136), int(36)))
        return image,rect

用modelFinemapping找出车牌左右边界的位置坐标,乘以原图的长image.shape[1],就找到了原图的车牌左右位置坐标,并分别用H,T表示最后是输出裁剪后的图像,这样就完成了车牌精定位,精准裁剪了车牌有文字部分的左右边界之间的图像

recognizeOne()函数

    def recognizeOne(self,src):
        x_tempx = src
        x_temp = cv2.resize(x_tempx,( 164,48))
        x_temp = x_temp.transpose(1, 0, 2)
        y_pred = self.modelSeqRec.predict(np.array([x_temp]))
        y_pred = y_pred[:,2:,:]
        return self.fastdecode(y_pred)

的功能就是对车牌上的文字进行识别。在经历了前两个函数依次粗定位、精定位和裁剪之后,已经得到了比较精确的车牌图片,图片上只有车牌,不包含其他内容。recognizeOne输入的就是裁剪过的车牌照片,输出的是车牌上的文字。recognizeOne函数中调用的是modelSeqRec.predict函数进行预测这个函数也是建立了一个卷积神经网络对图像进行处理,也进行了多次的卷积、激励和池化操作。此处的车牌字符信息识别不同于传统的字符识别方法,即先分割字符然后再逐一使用分类算法进行识别,而这里采用了OCR光学字符识别技术,不分割字符的前提下能够识别出车牌的七个字符。

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值