python使用KNN算法识别手写数字


Posted in Python onApril 25, 2019

本文实例为大家分享了python使用KNN算法识别手写数字的具体代码,供大家参考,具体内容如下

# -*- coding: utf-8 -*-
#pip install numpy
import os
import os.path
from numpy import *
import operator
import time
from os import listdir
 
"""
描述:
  KNN算法实现分类器
参数:
  inputPoint:测试集
  dataSet:训练集
  labels:类别标签
  k:K个邻居
返回值:
  该测试数据的类别
"""
def classify(inputPoint,dataSet,labels,k):
  dataSetSize = dataSet.shape[0] #已知分类的数据集(训练集)的行数
  #先tile函数将输入点拓展成与训练集相同维数的矩阵,再计算欧氏距离
  diffMat = tile(inputPoint,(dataSetSize,1))-dataSet #样本与训练集的差值矩阵
 
  # print(inputPoint);
  sqDiffMat = diffMat ** 2 #sqDiffMat 的数据类型是nump提供的ndarray,这不是矩阵的平方,而是每个元素变成原来的平方。
  sqDistances = sqDiffMat.sum(axis=1)  #计算每一行上元素的和
  # print(sqDistances);
  distances = sqDistances ** 0.5   #开方得到欧拉距离矩阵
  # print(distances);
  sortedDistIndicies = distances.argsort() #按distances中元素进行升序排序后得到的对应下标的列表,argsort函数返回的是数组值从小到大的索引值
  # print(sortedDistIndicies);
 
  # classCount数据类型是这样的{0: 2, 1: 2},字典key:value
  classCount = {}
  # 选择距离最小的k个点
  for i in range(k):
    voteIlabel = labels[ sortedDistIndicies[i] ]
    # print(voteIlabel)
    # 类别数加1
    classCount[voteIlabel] = classCount.get(voteIlabel,0)+1
  print(classCount)# {1: 1, 7: 2}
  #按classCount字典的第2个元素(即类别出现的次数)从大到小排序
  sortedClassCount = sorted(classCount.items(), key = operator.itemgetter(1), reverse = True)
  print(sortedClassCount)# [(7, 2), (1, 1)]
  return sortedClassCount[0][0]
 
"""
描述:
  读取指定文件名的文本数据,构建一个矩阵
参数:
  文本文件名称
返回值:
  一个单行矩阵
"""
def img2vector(filename):
 returnVect = []
 fr = open(filename)
 for i in range(32):
  lineStr = fr.readline()
  for j in range(32):
   returnVect.append(int(lineStr[j]))
 return returnVect
 
"""
描述:
  从文件名中解析分类数字,比如由0_0.txt得知这个文本代表的数字分类是0
参数:
  文本文件名称
返回值:
  一个代表分类的数字
"""
def classnumCut(fileName):
  fileStr = fileName.split('.')[0]
  classNumStr = int(fileStr.split('_')[0])
  return classNumStr
 
"""
描述:
  构建训练集数据向量,及对应分类标签向量
参数:
  无
返回值:
  hwLabels:分类标签矩阵
  trainingMat:训练数据集矩阵
"""
def trainingDataSet():
  hwLabels = []
  trainingFileList = listdir('trainingDigits')   #获取目录内容
  m = len(trainingFileList)
  # zeros返回全部是0的矩阵,参数是行和列
  trainingMat = zeros((m,1024))    #m维向量的训练集
  for i in range(m):
    # print (i);
    fileNameStr = trainingFileList[i]
    hwLabels.append(classnumCut(fileNameStr))
    trainingMat[i,:] = img2vector('trainingDigits/%s' % fileNameStr)
  return hwLabels,trainingMat
 
"""
描述:
  主函数,最终打印识别了多少个数字以及识别的错误率
参数:
  无
返回值:
  无
"""
def handwritingTest():
  """
  hwLabels,trainingMat 是标签和训练数据,
  hwLabels 是一个一维矩阵,代表每个文本对应的标签(即文本所代表的数字类型)
  trainingMat是一个多维矩阵,每一行都代表一个文本的数据,每行有1024个数字(0或1)
  """
  hwLabels,trainingMat = trainingDataSet() #构建训练集
  testFileList = listdir('testDigits') #获取测试集
  errorCount = 0.0    #错误数
  mTest = len(testFileList)    #测试集总样本数
  t1 = time.time()
  for i in range(mTest):
    fileNameStr = testFileList[i]
    classNumStr = classnumCut(fileNameStr)
    # img2vector返回一个文本对应的一维矩阵,1024个0或者1
    vectorUnderTest = img2vector('testDigits/%s' % fileNameStr)
    #调用knn算法进行测试
    classifierResult = classify(vectorUnderTest, trainingMat, hwLabels, 3)
    # 打印测试出来的结果和真正的结果,看看是否匹配
    print ("the classifier came back with: %d, the real answer is: %d" % (classifierResult, classNumStr))
    # 如果测试出来的值和原值不相等,errorCount+1
    if (classifierResult != classNumStr):
      errorCount += 1.0
  print("\nthe total number of tests is: %d" % mTest)   #输出测试总样本数
  print ("the total number of errors is: %d" % errorCount )  #输出测试错误样本数
  print ("the total error rate is: %f" % (errorCount/float(mTest))) #输出错误率
  t2 = time.time()
  print ("Cost time: %.2fmin, %.4fs."%((t2-t1)//60,(t2-t1)%60) ) #测试耗时
 
"""
描述:
  指定handwritingTest()为主函数
"""
if __name__ == "__main__":
 handwritingTest()

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Python 相关文章推荐
归纳整理Python中的控制流语句的知识点
Apr 14 Python
Python中使用ElementTree解析XML示例
Jun 02 Python
Python利用BeautifulSoup解析Html的方法示例
Jul 30 Python
python中pip的使用和修改下载源的方法
Jul 08 Python
python将类似json的数据存储到MySQL中的实例
Jul 12 Python
Flask教程之重定向与错误处理实例分析
Aug 01 Python
在Python3 numpy中mean和average的区别详解
Aug 24 Python
python处理excel绘制雷达图
Oct 18 Python
Python 根据数据模板创建shapefile的实现
Nov 26 Python
Pandas 解决dataframe的一列进行向下顺移问题
Dec 27 Python
如何实现更换Jupyter Notebook内核Python版本
May 18 Python
Python 实现简单的客户端认证
Jul 29 Python
Python3.5运算符操作实例详解
Apr 25 #Python
Python对象转换为json的方法步骤
Apr 25 #Python
Python+PyQt5实现美剧爬虫可视工具的方法
Apr 25 #Python
详解用python实现基本的学生管理系统(文件存储版)(python3)
Apr 25 #Python
Python基础教程之if判断,while循环,循环嵌套
Apr 25 #Python
python3通过selenium爬虫获取到dj商品的实例代码
Apr 25 #Python
NumPy 数组使用大全
Apr 25 #Python
You might like
PHP统计当前在线用户数实例讲解
2015/10/21 PHP
PHP面向对象程序设计之对象克隆clone和魔术方法__clone()用法分析
2019/06/12 PHP
通用于ie和firefox的函数 GetCurrentStyle (obj, prop)
2006/12/27 Javascript
jquery判断checkbox(复选框)是否被选中的代码
2010/10/20 Javascript
加载 Javascript 最佳实践
2011/10/30 Javascript
JS构建页面的DOM节点结构的实现代码
2011/12/09 Javascript
jquery中$.post()方法的简单实例
2014/02/04 Javascript
JS使用ajax从xml文件动态获取数据显示的方法
2015/03/24 Javascript
js带点自动图片轮播幻灯片特效代码分享
2015/09/07 Javascript
探究Javascript模板引擎mustache.js使用方法
2016/01/26 Javascript
Bootstrapvalidator校验、校验清除重置的实现代码(推荐)
2016/09/28 Javascript
Node.js websocket使用socket.io库实现实时聊天室
2017/02/20 Javascript
简述vue中的config配置
2018/01/23 Javascript
vue-for循环嵌套操作示例
2019/01/28 Javascript
ElementUI radio组件选中小改造
2019/08/12 Javascript
ES6基础之 Promise 对象用法实例详解
2019/08/22 Javascript
vue draggable resizable gorkys与v-chart使用与总结
2019/09/05 Javascript
uploadify插件实现多个图片上传并预览
2019/09/30 Javascript
[00:27]DOTA2战队VP、Secret贺新春
2018/02/11 DOTA
简单介绍Python的Django框架加载模版的方式
2015/07/20 Python
Python编程实现正则删除命令功能
2017/08/30 Python
基于循环神经网络(RNN)实现影评情感分类
2018/03/26 Python
浅谈tensorflow中几个随机函数的用法
2018/07/27 Python
Python数据预处理之数据规范化(归一化)示例
2019/01/08 Python
Python设计模式之职责链模式原理与用法实例分析
2019/01/11 Python
详解python中init方法和随机数方法
2019/03/13 Python
详解Anconda环境下载python包的教程(图形界面+命令行+pycharm安装)
2019/11/11 Python
Python实现基于socket的udp传输与接收功能详解
2019/11/15 Python
python关于调用函数外的变量实例
2019/12/26 Python
新西兰廉价汽车租赁:Snap Rentals
2018/09/14 全球购物
应届生人事助理求职信
2013/11/09 职场文书
四风问题自查报告剖析材料
2014/02/08 职场文书
新员工考核评语
2014/12/31 职场文书
导游词之湖州-太湖
2019/10/11 职场文书
MySQL 数据丢失排查案例
2021/05/08 MySQL
使用Pytorch训练two-head网络的操作
2021/05/28 Python