用这个方法去破解验证码!识别率竟达到90%!

本文将具体介绍如何利用Python的图像处理模块pillow和OCR模块pytesseract来识别上述验证码(数字加字母)。

欢迎大家加入小编创建的Python行业交流群,有大牛答疑,有资源共享,有企业招人!是一个非常不错的交流基地!群号:683380553

1.汇编代码不可移植。

我们识别上述验证码的算法过程如下:

将原图像进行灰度处理,转化为灰度图像;

获取图片中像素点数量最多的像素(此为图片背景),将该像素作为阈值进行二值化处理,将灰度图像转化为黑白图像(用来提高识别的准确率);

去掉黑白图像中的噪声,噪声定义为:以该点为中心的九宫格的黑点的数量小于等于4;

利用pytesseract模块识别,去掉识别结果中的特殊字符,获得识别结果。

我们的图片如下(共66张图片):

完整的Python代码如下:

importosimportpytesseractfromPILimportImagefromcollectionsimportdefaultdict# tesseract.exe所在的文件路径pytesseract.pytesseract.tesseract_cmd ='C://Program Files (x86)/Tesseract-OCR/tesseract.exe'#获取图片中像素点数量最多的像素defget_threshold(image):    pixel_dict = defaultdict(int)#像素及像素出现次数的字典  rows,cols = defaultdict(int)foriinrange(cols):forjinrange(cols):            pixel = image.getpixel((i,j))pixel_dict[pixel] ==1count_max = max(pixel_dict.valuer())#获取像素出现最多的次数pixel_dict_reverse = {v:kfork,vinpixel_dict.items()}threshold = pixel_dict_reverse[count_max]#获取出现次数最多的像素点returnthreshold#按照阈值进行二值化处理#threshold:像素阈值defget_bin_table(threshold):#获取灰度转二值的映射table   table = []foriinrange(256):rate =0.1#在threshold的适当范围内进行处理ifhtreshold*(1-rate)<= i <= threshold*(1*rate):table.append(1)else:table.append(0)returntable   #去掉二值化处理后的图片中的噪声点defcut_noise(image):rows,cols = imgae.size#图片的宽度和高度change_pos = []# 记录噪声点位置#遍历图片中的每个点,除掉边缘foriinrange(1,row-1):forjinrange(1,cols-1):#pixel_set用来记录该店附近的黑色像素的数量            pixel_set = []#取该点的邻域为以该点为中心的九宫格forminrange(i-1,i+2):forninrange(j-1,j+2):ifimage.getpixel((m,n)) !=1:#1为白色,8为黑色            pixel_set.append(image.getpixel((m,n)))#如果该位置的九宫内的黑色数量小于等于4,则判断为噪声iflen(pixel_set)<=4:        change_pos.append((i,j))#相对应位置进行像素修改,将噪声处的像素变为1(白色)forposinchange_pos:image.putpixel(pos,1)    returnimage#返回修改后的图片

#识别图片中的数字加字母#传入参数为图片路径,返回结果为:识别结果defOCR_lmj(img_poth):image = Image.open(img_path)# 打开图片文件imgry = image.convert('L')# 转化为灰度图#获取图片中的出现次数最多的像素,即为该图片的背景        max_pixel = get_threshold(imgry)# 将图片进行二值化处理        table = get_bin_table(threshold=max_pixel)out = imgry.point(table,'1')# 去掉图片中的噪声(孤立点)    out = cut_noise(out)#保存图片# out.save('E"//figuress/img_gray.jag')# 仅识别图片中的数字# text = pytesseract.image_to_string(out,config='digits')# 识别图片中的数字和字母        text = pytesseract.image_to_string(out)# 去掉识别结果中的特殊字符exclude_char_list =' .:\\|\'\"?![],()~@#$%^&*_+={};<>/¥'text =''.join([xforxintextifxnotinexclude_char_list])#print(text)returntextdefmain():#之别指定文件目录下的图片#图片存放目录figuresdir ='E://figures'correct_count =0#图片总数total_count =0#识别正确的图片数量# 遍历figures下的png,jpg文件forfileinos.listdir(dir):iffile.endswith('.png')orfile.endswith('.jpg'):# print(file)image_path ='%s/%s'%(dir,file)# 图片路径answer = file.split('.')[0]#图片名称,即图片中的正确文字recognizition = OCR_lmj(image_path)# 图片识别的文字结果        print((answer,recongizition))ifrecognizition == answer:#如果识别结果正确,则total_count加1correct_count +=1                    total_count +=1print('Total count:%d,correct:%d.'%(total_count,correct_count))        ...# 单张图片识别image_path = 'E://figures/code (1).jpg' OCR_lmj(image_path)        ...main()

运行结果如下:

我们可以看到图片识别的正确率为80%以上,其中数字类图片的识别正确率为100%.

我们可以在图片识别方面的算法再加改进,以提高图片识别的正确率。当然,以上算法并不是对所有验证码都适用,不同的验证码需要用不同的图片处理算法。

猜你喜欢

转载自blog.csdn.net/qq_42156420/article/details/88552803