在人工智能计算机视觉方面,有图像分类、目标检测、语义分割、实例分割四大主要任务。目前在各个领域都有比较成熟的应用。

在一些特定的环境或特殊需求中,我们可能需要通过图像来对水表进行智能读数。

python时刻预测(73.Python语义分割后期处理)(1)

水表数据图像

对于水表读数,首先考虑使用语义分割,目的就是把水表盘的数据区域分割出来。关于语义分割可以参看:5.人工智能-语义分割。本文主要想讲一下语义分割后的图像数据处理和识别。

语义分割后,返回的是多边形坐标值。这里因为可以看到水表的数据区域并不是水平的,所以我们需要根据返回的多边形坐标值,对水表的数据区域图像进行旋转后得到,再进行文字识别。

这里每个水表图像对应一个文本文件,文件内容就是语义分割后返回的4个顶点的坐标值。如:97 475 280 424 293 466 105 520

python时刻预测(73.Python语义分割后期处理)(2)

演示数据

实现代码:

import cv2 import os import numpy as np import paddleocr basedir="meter" ptslst=[] #读取文本文件 for f in os.listdir(basedir): #分离文件名和后缀 fname,fext=os.path.splitext(f) if fext==".txt": #读取文件 with open(os.path.join(basedir,f)) as f: for line in f: #按照空格分割,并转换为int x1,y1,x2,y2,x3,y3,x4,y4,v=list(map(lambda x:int(x),line.split())) #print(x1,y1,x2,y2,x3,y3,x4,y4,v) dxy={fname:[[x1,y1],[x2,y2],[x3,y3],[x4,y4]]} ptslst.append(dxy) #print(ptslst) #多边形旋转为矩形,并计算旋转角度,返回旋转后的矩形,中心坐标 def rotate_rect(pts): #计算多边形的中心点 x=sum(map(lambda x:x[0],pts))/4 y=sum(map(lambda x:x[1],pts))/4 #计算多边形的长宽 w=max(map(lambda x:x[0],pts))-min(map(lambda x:x[0],pts)) h=max(map(lambda x:x[1],pts))-min(map(lambda x:x[1],pts)) #计算多边形的旋转角度 angle=np.arctan2(pts[1][1]-pts[0][1],pts[1][0]-pts[0][0])*180/np.pi #旋转后的矩形 pts_rotate=np.array([[x-w/2,y-h/4],[x w/2,y-h/4],[x w/2,y h/4],[x-w/2,y h/4]]) pts_rotate=pts_rotate.astype(np.int32) return pts_rotate,angle,x,y #以(x,y)为中心旋转图像 def rotate_img(img,angle,x,y): #获取图像的高和宽 h,w=img.shape[:2] #计算旋转后的高和宽 h_new=int(np.sqrt(h**2 w**2-2*h*w*np.cos(angle))) w_new=int(np.sqrt(h**2 w**2 2*h*w*np.cos(angle))) #计算旋转后的中心点 # x_new=w_new/2 # y_new=h_new/2 #计算旋转矩阵 # M=cv2.getRotationMatrix2D((x_new,y_new),angle,1) M=cv2.getRotationMatrix2D((x,y),angle,1) #旋转图像 img_rotate=cv2.warpAffine(img,M,(w_new,h_new)) return img_rotate #读取图片,并画多边形 for f in os.listdir(basedir): #分离文件名和后缀 fname,fext=os.path.splitext(f) if fext==".jpg": #读取图片 img=cv2.imread(os.path.join(basedir,f)) #画多边形 for dxy in ptslst: if fname in dxy: #转换为np.array pts=np.array(dxy[fname]) #cv2.polylines(img,[pts],True,(0,255,0),2) #返回旋转后坐标,旋转角度,中心点 pts_m,theta,x,y=rotate_rect(pts) #print(pts_m) #旋转图像 img=rotate_img(img,theta,x,y) #cv2.polylines(img,[pts_m],True,(0,0,255),2) #获取旋转后矩形的图像 roi_img=img[pts_m[0][1]:pts_m[2][1],pts_m[0][0]:pts_m[2][0]] #ocr识别 ocr=paddleocr.PaddleOCR(use_angle_cls=True,lang="ch") result=ocr.ocr(roi_img,cls=True) line=result[0] boxes=line[0] txts=line[1][0] scores=line[1][1] #print(boxes,txts,scores) #写文字 cv2.putText(roi_img,txts,(10,25),cv2.FONT_HERSHEY_SIMPLEX,1,(0,0,255),2) cv2.imshow("meter",roi_img) #显示图片 #cv2.imshow("img",img) cv2.waitKey(0) cv2.destroyAllWindows()

实现效果

python时刻预测(73.Python语义分割后期处理)(3)

旋转后识别结果

,