一、k-近邻算法

1. k-近邻法简介
k近邻法(k-nearest neighbor, k-NN)是1968年由Cover THart 提出的一种基本分类与回归方法。它的工作原理是:存在一个样本数据集合,也称作为训练样本集,并且样本集中每个数据都存在标签,即我们知道样本集中每一个数据与所属分类的对应关系。输入没有标签的新数据后,将新的数据的每个特征与样本集中数据对应的特征进行比较,然后算法提取样本最相似数据(最近邻)的分类标签。一般来说,我们只选择样本数据集中前k个最相似的数据,这就是k-近邻算法中k的出处,通常k是不大于20的整数。最后,选择k个最相似数据中出现次数最多的分类,作为新数据的分类。

注意: k-近邻法不具有显式的学习过程,它实际上是利用训练数据集对特征向量空间进行划分,并作为其分类的“模型”.其中K值的选取、距离度量及分类决策规则是k近邻算法的三个基本要素。

2. k近邻算法的数学语言表达:

3. k近邻算法中k值的选取标准:

4. 在k近邻算法中的距离度量公式如下图所示:

5. k-近邻算法中的分类决策规则

6. K近邻算法的一般流程

  1. 计算已知类别数据集中的点与当前点之间的距离;
  2. 按照距离递增次序排序;
  3. 选取与当前点距离最小的k个点;
  4. 确定前k个点所在类别的出现频率;
  5. 返回前k个点出现频率最高的类别作为当前点的预测分类

二、k-近邻算法案列实战:实现电影分类

本次案例主要是使用k-近邻算法来对电影进行分类。这里我们主要将电影分为两种:爱情片和动作片。根据电影中出现的打斗和接吻镜头来进行判定。本案例所使用的距离度量为欧氏距离。

  1. 准备数据集

    结果显示:
  2. 根据欧式距离公式,计算距离,选择距离最小的前k个点。根据你输入的电影数据信息,程序返回分类结果。
    程序代码如下:
def classify0(inX, dataSet, labels, k):dataSetSize = dataSet.shape[0]diffMat = np.tile(inX, (dataSetSize, 1)) - dataSetsqDiffMat = diffMat**2sqDistances = sqDiffMat.sum(axis=1)distances = sqDistances**0.5sortedDistIndices = distances.argsort()classCount = {}for i in range(k):voteIlabel = labels[sortedDistIndices[i]]classCount[voteIlabel] = classCount.get(voteIlabel,0) + 1sortedClassCount = sorted(classCount.items(),key=operator.itemgetter(1),reverse=True)#返回次数最多的类别,即所要分类的类别return sortedClassCount[0][0]if __name__ == '__main__':#创建数据集group, labels = createDataSet()#对输入数据进行分类x = input("请输入测试数据:")xlist=x.split(" ")test = [int(xlist[i]) for i in range(len(xlist))]#kNN分类test_class = classify0(test, group, labels, 3)#打印分类结果print(test_class)

结果如下:

三、k-近邻算法案例实战:手写数字识别系统

本节我们一步步地构造使用k-近邻分类器的手写识别系统。为了简单起见,这里构造的系统
只能识别数字0到9.需要识别的数字已经使用图形处理软件,处理成具有相同的色
彩和大小,其中宽高是32像素×32像素的黑白图像。尽管采用文本格式存储图像不能有效地利用内
存空间,但是为了方便理解,我们还是将图像转换为文本格式。
存储的数字文件格式为:数字的值_该数字的样本序号,如下图所示:

数据集分为训练集和测试集,通过上述电影分类的方法,设计一个k-近邻算法分类器实现数字分类。其中数据集和实现代码下载地址:数据集下载

代码展示:

import numpy as np
import operator
from os import listdirdef classify0(inX, dataSet, labels, k):dataSetSize = dataSet.shape[0]#欧式距离计算 diffMat = tile(inX, (dataSetSize,1)) - dataSetsqDiffMat = diffMat**2sqDistances = sqDiffMat.sum(axis=1)distances = sqDistances**0.5sortedDistIndicies = distances.argsort()     classCount={} #选择距离最小的K个点for i in range(k):voteIlabel = labels[sortedDistIndicies[i]]classCount[voteIlabel] = classCount.get(voteIlabel,0) + 1sortedClassCount = sorted(classCount.items(), key=operator.itemgetter(1), reverse=True)return sortedClassCount[0][0]def img2vector(filename):returnVect = np.zeros((1,1024))fr = open(filename)for i in range(32):lineStr = fr.readline()for j in range(32):returnVect[0,32*i+j] = int(lineStr[j])return returnVectdef handwritingClassTest():hwLabels = []trainingFileList = listdir('trainingDigits')           #load the training setm = len(trainingFileList)trainingMat = np.zeros((m,1024))for i in range(m):fileNameStr = trainingFileList[i]fileStr = fileNameStr.split('.')[0]     #take off .txtclassNumStr = int(fileStr.split('_')[0])hwLabels.append(classNumStr)trainingMat[i,:] = img2vector('trainingDigits/%s' % fileNameStr)testFileList = listdir('testDigits')        #iterate through the test seterrorCount = 0.0mTest = len(testFileList)for i in range(mTest):fileNameStr = testFileList[i]fileStr = fileNameStr.split('.')[0]     #take off .txtclassNumStr = int(fileStr.split('_')[0])vectorUnderTest = img2vector('testDigits/%s' % fileNameStr)classifierResult = classify0(vectorUnderTest, trainingMat, hwLabels, 3)print("the classifier came back with: %d, the real answer is: %d" % (classifierResult, classNumStr))if (classifierResult != classNumStr): errorCount += 1.0print("\nthe total number of errors is: %d" % errorCount)print("\nthe total error rate is: %f" % (errorCount/float(mTest)))

识别结果如下所示:

四、总结

kNN算法的优缺点
优点:

  • 简单好用,容易理解,精度高,理论成熟,既可以用来做分类也可以用来做回归;
  • 可用于数值型数据和离散型数据;
  • 训练时间复杂度为O(n);无数据输入假定;
  • 对异常值不敏感

缺点:

  • 计算复杂性高;空间复杂性高;
  • 样本不平衡问题(即有些类别的样本数量很多,而其它样本的数量很少);
  • 一般数值很大的时候不用这个,计算量太大。但是单个样本又不能太少,否则容易发生误分。
  • 最大的缺点是无法给出数据的内在含义。

参考资料:
本文中提到的电影分类、手写数字识别实例和数据集,均来自于《机器学习实战》的第二章k-近邻算法。
本文的算法理论部分,参考自《统计学习方法 李航》的第三章k近邻法以及《机器学习实战》的第二章k-近邻算法。

机器学习实战(一):K-近邻算法(史上最全干货) 算法总结+案例实战相关推荐

  1. 史上最全的 MySQL 高性能优化实战总结

    转载自   史上最全的 MySQL 高性能优化实战总结 一.前言 MySQL 对于很多 Linux 从业者而言,是一个非常棘手的问题,多数情况都是因为对数据库出现问题的情况和处理思路不清晰.在进行 M ...

  2. YOLO算法史上最全综述:从YOLOv1到YOLOv5

    作者:初识cv,编辑:极市平台 来源丨https://zhuanlan.zhihu.com/p/136382095,侵删 导读 YOLO系列是基于深度学习的回归方法,本文详细介绍了从YOLOv1至最新 ...

  3. 收藏起来,史上最全的 MySQL 高性能优化实战总结!

    一.前言 MySQL 对于很多 Linux 从业者而言,是一个非常棘手的问题,多数情况都是因为对数据库出现问题的情况和处理思路不清晰.在进行 MySQL 的优化之前必须要了解的就是 MySQL 的查询 ...

  4. 史上最全的MySQL高性能优化实战总结!

    https://www.jianshu.com/p/4af41b682e06 1.1 前言 MySQL对于很多Linux从业者而言,是一个非常棘手的问题,多数情况都是因为对数据库出现问题的情况和处理思 ...

  5. 史上最全排序算法总结!建议收藏

    作者 | 铁猴 责编 | 屠敏 出品 | CSDN 博客  简介 本文对常见排序算法进行总结. 排序算法 冒泡排序 该算法比较简单,几乎所有语言涉及到算法时,都会涉及到冒泡算法. 算法思路: 比较相邻 ...

  6. 史上最全数据结构算法之递归系列学习,建议收藏!

    写在前边 接下来分享的文章是关于递归的,这篇文章不单单分享递归的一切,我觉得更重要的是向每位读者传递一个思想.思想?对的,没错!这篇文章不能说包含递归的边边角角,但是通过自己的理论上的学习和实践,有了 ...

  7. 史上最全排序算法总结 | 原力计划

    作者 | 铁猴 责编 | 屠敏 出品 | CSDN 博客  简介 本文对常见排序算法进行总结. 排序算法 冒泡排序 该算法比较简单,几乎所有语言涉及到算法时,都会涉及到冒泡算法. 算法思路: 比较相邻 ...

  8. mysql 幂运算_算法—史上最好快速幂算法讲解

    前言 快速幂是什么?顾名思义,快速幂就是快速算底数的n次幂. 有多快?其时间复杂度为 O(log₂n), 与朴素的O(n)相比效率有了极大的提高. 用的多么?快速幂属于数论的范畴,本是ACM经典算法, ...

  9. linux sort 源码_Linux: 史上最全的sort命令案例,打包带走吧

    一. 介绍 sort命令是用来对文字内容(文档)排序使用的.同时也可以排序去重.指定字段排序,按照月份排序.按照数字排序,检查文件是否有序等等.默认情况是按照字典序排序以后标准输出到屏幕上,但是该命令 ...

  10. 史上最全系列 | 大数据框架知识点汇总(资源分享、还不快拿去)

    前言 大家好,我是土哥 写文章整整 五个月 了,在这期间写了很多篇高质量文章,每一篇都在 1000+ 阅读以上,为了让各位小伙伴更好的学习和面试,我将自己 发表的文章 以及 未发表的文章 全部汇总成一 ...

最新文章

  1. 我理解的分类、目标检测、目标识别、目标定位、目标跟踪
  2. [导入]创建笔 (Visual C#)
  3. SCCM管理 - 更新部署
  4. Markdown设置字体大小、颜色...,CSDN博客编写设置字体大小、颜色、粗细。字体,文字背景设置。
  5. generator (1)
  6. 程序员如何用Java排序
  7. MySQL—修改数据库root用户密码
  8. python核心装饰_《python核心编程》中高级闭包和装饰器理解?
  9. 【服务器环境搭建-Centos】tmpfs,【转载】
  10. 20191202_2_识别偷税漏税人
  11. 拯救行动第二季 - 答题赢游戏机活动已经开放!
  12. i3-9100f和i5-9400f 的区别
  13. java投屏 dlna 安卓_DLNA投屏
  14. Android 打开系统文件管理器选择文件
  15. C#图形界面汉诺塔Hanoi
  16. 如何上传到GitHub的main分支而不是master分支
  17. 企业微信没有50名员工如何扩容?如何突破企业微信50000客户数的限制?企业微信如何扩容10万客户?
  18. 蓝奏云打不开解决方法
  19. C#中线程安全的单例模式
  20. AI 硬件加速的重大飞跃!可训练机器学习硬件的光学芯片

热门文章

  1. 汉王手写输入法android,汉王手写输入法
  2. VARCHART XGantt_v5.1用户手册:如何把控件放在表单上
  3. matlab怎么绘制球差像差曲线,减小球差的环带透镜设计
  4. echarts 生成 迁徙图_echarts迁徙图
  5. 搜索引擎四:CoreSeek配置MySql数据源
  6. flv格式php怎么播放不了,FLV格式视频不能在网页播放的解决办法
  7. 腾讯力作!iOS 9 人机界面指南(5):图标与图形设计
  8. 实现qq空间自动化点赞
  9. PDF编辑器中文版免费下载哪里可以下载?
  10. learn git 廖雪峰GIT教材1 创建与合并分支