文章目录

  • 【机器学习】KNN算法实现手写板字迹识别
    • 1. 前言
    • 2. 实验背景
    • 3. 测试过程
      • 3.1 手写板及测试数据的制作
      • 3.2 加载训练数据并进行KNN模型搭建
      • 3.3 结果预测
    • 4. 总结

【机器学习】KNN算法实现手写板字迹识别

1. 前言

​ 上篇博客通过KNN算法实现鸢尾花数据集分类,在博客最后对KNN算法是否适合于图像分类进行了讨论。本篇博客通过KNN算法实现手写板字迹识别,通过人机交互的模式验证KNN算法是否合适于图像分类。

2. 实验背景

​ 在制作手写体数据集的过程中,常会出现训练数据和测试数据都是出自同一个人的笔迹,此时KNN模型对测试数据友好,但这其实并不符合实际情况。因此本次实验将不同人的笔迹作为训练集,为了增加人机交互性,我们实现了一个简单的手写板进行测试集的制作。

数据集类型 数据集来源 数据集个数
训练集 收集不同人群的手写体,并转换成01矩阵的txt文件格式 1974
测试集 通过python实现手写板,将自己的手写体作为测试集进行预测 1

3. 测试过程

测试步骤:
1. 设计手写板
2. 制作测试数据
3. 加载训练数据
4. 通过KNN算法进行训练
5. 得到预测结果

3.1 手写板及测试数据的制作

基本思路:通过手写板写入内容,将其保存为图片(512 x 512)。再将图片转换为01矩阵(32 x 32)并保存为txt文件格式作为测试数据。

# 手写板,通过opencv实现
def draw(event,x,y,flags,param):global ix,iyif event==cv2.EVENT_LBUTTONDOWN:drawing=Trueix,iy=x,yelif event==cv2.EVENT_MOUSEMOVE:if drawing==True:cv2.circle(img,(x,y),30,(0,0,0),-1)elif event==cv2.EVENT_LBUTTONUP:drawing=Falseif __name__ == "__main__":# 通过手写板制作图片测试集img=np.zeros((512,512,3),np.uint8)for i in range(512):img[i,:]=255cv2.namedWindow('image')cv2.setMouseCallback('image',draw)while(1):cv2.imshow('image',img)if cv2.waitKey(1) & 0xFF == ord(' '):cv2.imwrite('1.jpg',img)breakcv2.destroyAllWindows()# 将图片转换为0,1矩阵并记录在txt文件中img1 = cv2.imread('1.jpg', cv2.IMREAD_GRAYSCALE)res=cv2.resize(img1,(32,32),interpolation=cv2.INTER_CUBIC)pic=[]for i in range(32):for j in range(32):if res[i][j]<=200:res[i][j]=1else:res[i][j]=0pic.append(int(res[i][j]))filename = 'out.txt'with open(filename, 'w') as name:for i in range(32*32):name.write(str(pic[i]))if (i+1) % 32 == 0:name.write("\n")


3.2 加载训练数据并进行KNN模型搭建

​ 这里的KNN算法与之前鸢尾花分类的算法一样,首先将测试数据按照训练数据维度进行转换,并通过欧式距离进行排序(鸢尾花分类通过计算每条数据之间的距离;字迹识别通过计算每张图片之间的距离),最后选出K个最近的数据并筛选频率最高的标签作为预测结果。

​ 数据加载方式的差别有两个,第一是尺寸信息更丰富,需要将(32,32)维度转为(1,1024)维度方便欧氏距离的计算;第二是标签需要自己设置,这里采用常见的文件名分类法。

# 图像转向量,将(32,32)转为(1,1024),目的在于实现KNN算法的距离计算
def img2vector(filename):vector = np.zeros((1, 1024))file = open(filename)for i in range(32):str = file.readline()for j in range(32):vector[0, 32*i+j] = int(str[j])return vectordef KNN(Test, Train, labels, k):dataSetSize = Train.shape[0]# 求像素的欧氏距离distance = np.tile(Test, (dataSetSize, 1)) - Train    sqdistance = distance ** 2sqdistances = sqdistance.sum(axis=1)distances = sqdistances ** 0.5 # 得到训练集的下标sortedDistIndicies = distances.argsort()# 得到K个欧式距离最近的labelresult = []for i in range(k):voteIlabel = labels[sortedDistIndicies[i]]result.append(voteIlabel)print(result)collection = Counter(result)result = collection.most_common(1)return result[0][0]def main():# 载入处理训练集和标签labels = []Train_list = listdir('knn/digits/trainingDigits')batch = len(Train_list)Train = np.zeros((batch, 1024))for i in range(batch):name = Train_list[i]    # name得到每个文件名称,"0_0.txt"filename = name.split('.')[0].split('_')[0]labels.append(filename)    # filename表示标签列表Train[i, :] = img2vector('knn/digits/trainingDigits/%s' % name)# 这里我设计的是将手写板的图像转换为0,1矩阵并记入txt中作为测试集Test = img2vector("out.txt")result = KNN(Test, Train, labels, 3)print(result)

3.3 结果预测

训练数据:
链接:https://pan.baidu.com/s/1Zh0rYwvovmm4drEOpjLS8A
提取码:mjll

全部代码:

import cv2
import numpy as np
from os import listdir
import operator
from collections import Counterdrawing=False# 图像转向量,将(32,32)转为(1,1024),目的在于实现KNN算法的距离计算
def img2vector(filename):vector = np.zeros((1, 1024))file = open(filename)for i in range(32):str = file.readline()for j in range(32):vector[0, 32*i+j] = int(str[j])return vectordef KNN(Test, Train, labels, k):dataSetSize = Train.shape[0]# 求像素的欧氏距离distance = np.tile(Test, (dataSetSize, 1)) - Train    sqdistance = distance ** 2sqdistances = sqdistance.sum(axis=1)distances = sqdistances ** 0.5 # 得到训练集的下标sortedDistIndicies = distances.argsort()# 得到K个欧式距离最近的labelresult = []for i in range(k):voteIlabel = labels[sortedDistIndicies[i]]result.append(voteIlabel)print(result)collection = Counter(result)result = collection.most_common(1)return result[0][0]def main():# 载入处理训练集和标签labels = []Train_list = listdir('knn/digits/trainingDigits')batch = len(Train_list)Train = np.zeros((batch, 1024))for i in range(batch):name = Train_list[i]    # name得到每个文件名称,"0_0.txt"filename = name.split('.')[0].split('_')[0]labels.append(filename)    # filename表示标签列表Train[i, :] = img2vector('knn/digits/trainingDigits/%s' % name)# 这里我设计的是将手写板的图像转换为0,1矩阵并记入txt中作为测试集Test = img2vector("out.txt")result = KNN(Test, Train, labels, 3)print("预测结果:", result)# 手写板,通过opencv实现
def draw(event,x,y,flags,param):global ix,iy,drawingif event==cv2.EVENT_LBUTTONDOWN:drawing=Trueix,iy=x,yelif event==cv2.EVENT_MOUSEMOVE:if drawing==True:cv2.circle(img,(x,y),30,(0,0,0),-1)elif event==cv2.EVENT_LBUTTONUP:drawing=Falseif __name__ == "__main__":# 通过手写板制作图片测试集img=np.zeros((512,512,3),np.uint8)for i in range(512):img[i,:]=255cv2.namedWindow('image')cv2.setMouseCallback('image',draw)while(1):cv2.imshow('image',img)if cv2.waitKey(1) & 0xFF == ord(' '):cv2.imwrite('1.jpg',img)breakcv2.destroyAllWindows()# 将图片转换为0,1矩阵并记录在txt文件中img1 = cv2.imread('1.jpg', cv2.IMREAD_GRAYSCALE)res=cv2.resize(img1,(32,32),interpolation=cv2.INTER_CUBIC)pic=[]for i in range(32):for j in range(32):if res[i][j]<=200:res[i][j]=1else:res[i][j]=0pic.append(int(res[i][j]))filename = 'out.txt'with open(filename, 'w') as name:for i in range(32*32):name.write(str(pic[i]))if (i+1) % 32 == 0:name.write("\n")# 开始测试main()

4. 总结

​ 大家有兴趣可以直接copy运行看看,预测结果还算可观。但相比深度学习方法精度略显不足。这是因为图片的语义信息是高级信息,无法通过常规的聚类以及距离进行语义判定。我们在做KNN实验时可以尝试输出测试数据与每个训练数据之间的距离,当样本足够时会发现距离相同的样本并不少且标签还不同,这就体现除了KNN算法的一个bug。

​ 总结得出,KNN算法可以在简单的图像数据上进行测试(例如:灰度数据),但在RGB图像甚至更加高维的数据上并不适用。

【机器学习】KNN算法实现手写板字迹识别相关推荐

  1. 课程设计(毕业设计)—基于机器学习KNN算法手写数字识别系统—计算机专业课程设计(毕业设计)

    机器学习KNN算法手写数字识别系统 下载本文手写数字识别系统完整的代码和课设报告的链接(或者可以联系博主koukou(壹壹23七2五六98),获取源码和报告):https://download.csd ...

  2. Python3:《机器学习笔记与实战》之Knn算法(2)识别手写数字

    Python3:<机器学习笔记与实战>之Knn算法(2)识别手写数字 转载请注明作者和出处:https://blog.csdn.net/weixin_41858342/article/de ...

  3. 机器学习knn算法学习笔记使用sklearn库 ,莺尾花实例

    ** 机器学习knn算法学习笔记使用sklearn库 ,莺尾花实例. 具体knn算法是怎样的我这里就不再详细论述.在这里我注意总结我使用knn算法进行一个分类的分析 ** 分析过程 1.前期准备 引入 ...

  4. 基于KNN算法的手写体数字识别

    基于KNN算法的手写体数字识别 KNN分类算法是一种经典的分类算法,属于懒惰学习算法的一种. 1.算法原理 工作原理:存在一个样本数据集合,也称作训练样本集,并且样本集中每个数据都存在标签,即我们知道 ...

  5. 【Python】基于kNN算法的手写识别系统的实现与分类器测试

    基于kNN算法的手写识别系统 1.      数据准备 使用windows画图工具,手写0-9共10个数字,每个数字写20遍,共200个BMP文件. 方法如下,使用画图工具,打开网格线,调整像素为32 ...

  6. 机器学习KNN算法实践:预测城市空气质量

    出品:Python数据之道 作者:叶庭云 整理:Lemon 机器学习KNN算法实践 预测城市空气质量 「Python数据之道」导读: 之前在公众号上分享过 "图解KNN算法" 的内 ...

  7. knn算法测试手写识别系统准确率

    手写识别系统,KNN算法实现手写识别系统的准确率 (准确率=测试分对的样本数/总的样本数) import numpy as np from itertools import chain from os ...

  8. 机器学习 —— KNN算法简单入门

    机器学习 -- KNN算法简单入门 第1关:手动实现简单kNN算法 1 KNN算法简介 1.1 kNN 算法的算法流程 1.2 kNN 算法的优缺点 1.3 编程要求+参数解释 2. 代码实现 3. ...

  9. 机器学习——KNN算法

    机器学习--KNN算法 文章目录 机器学习--KNN算法 前言 一.KNN原理基础 二.sklearn的基本建模流程 三.KNN算法调优:选取最优的K值 四.KNN中距离的相关讨论 1. KNN使用的 ...

最新文章

  1. android 52 粘滞广播
  2. Anaconda环境下OpenCV的安装
  3. 初学者自学python要看什么书-初学者如何学习Python?掌握这17个实用小技巧快速入门!...
  4. WF,WPF,Silverlight的DependencyProperty 附加属性
  5. Android快速阅读依赖的代码,Java Android快速阅读完整文件
  6. recv 和 send 阻塞和非阻塞的区别
  7. 浅谈分布式一致性:Raft 与 SOFAJRaft
  8. Linux 便笺技巧专栏
  9. win32调用系统颜色对话框
  10. LeetCode 5364. 按既定顺序创建目标数组
  11. 指纹支付为什么没有推广?
  12. android MVC
  13. 计算机网络 自顶向下方法 第四章 网络层
  14. ActiveMQ下载安装使用教程
  15. HG_REPMGR configure配置
  16. [前端积累]--响应式布局(三)
  17. 数据科学和机器学习中的优化理论与算法(下)
  18. 如何让你的Linux程序程序后台运行
  19. “熊孩子”乱敲键盘就攻破了Linux桌面,大神:17年前我就警告过你们
  20. 硬件防火墙 与软件防火墙

热门文章

  1. 免费SSH账号申请网址
  2. 2020.12.03丨全长转录组之基因和转录本鉴定
  3. 设计模式 | 解释器模式及典型应用
  4. 炫界 (302) -(查动简)_小米有品又玩极简石英表?这块表确实不一样
  5. vc cdatabase oracle,VC程序访问Oracle数据库的存储过程时的问题解决方案
  6. 如何洞悉人性、洞察人心
  7. java for循环遍历解释_三种for循环遍历
  8. ArcGIS API for JavaScript web前端应用
  9. 用CSS3写一个旋转轮播图
  10. 前端组件从零之垂直导航栏