Python K最近邻从原理到实现的方法


Posted in Python onAugust 15, 2019

本来这篇文章是5月份写的,今天修改了一下内容,就成今天发表的了,CSDN这是出BUG了还是什么改规则了。。。

引文:决策树和基于规则的分类器都是积极学习方法(eager learner)的例子,因为一旦训练数据可用,他们就开始学习从输入属性到类标号的映射模型。一个相反的策略是推迟对训练数据的建模,直到需要分类测试样例时再进行。采用这种策略的技术被称为消极学习法(lazy learner)。最近邻分类器就是这样的一种方法。

注:KNN既可以用于分类,也可以用于回归。

1.K最近邻分类器原理

首先给出一张图,根据这张图来理解最近邻分类器,如下:

Python K最近邻从原理到实现的方法

根据上图所示,有两类不同的样本数据,分别用蓝色的小正方形红色的小三角形表示,而图正中间的那个绿色的圆所标示的数据则是待分类的数据。也就是说,现在, 我们不知道中间那个绿色的数据是从属于哪一类(蓝色小正方形or红色小三角形),下面,我们就要解决这个问题:给这个绿色的圆分类。

我们常说,物以类聚,人以群分,判别一个人是一个什么样品质特征的人,常常可以从他or她身边的朋友入手,所谓观其友,而识其人。我们不是要判别上图中那个绿色的圆是属于哪一类数据么,好说,从它的邻居下手。但一次性看多少个邻居呢?从上图中,你还能看到:

  • 如果K=3,绿色圆点的最近的3个邻居是2个红色小三角形和1个蓝色小正方形,少数从属于多数,基于统计的方法,判定绿色的这个待分类点属于红色的三角形一类。
  • 如果K=5,绿色圆点的最近的5个邻居是2个红色三角形和3个蓝色的正方形,还是少数从属于多数,基于统计的方法,判定绿色的这个待分类点属于蓝色的正方形一类。

于此我们看到,当无法判定当前待分类点是从属于已知分类中的哪一类时,我们可以依据统计学的理论看它所处的位置特征,衡量它周围邻居的权重,而把它归为(或分配)到权重更大的那一类。这就是K近邻算法的核心思想。其关键还在于K值的选取,所以应当谨慎。

KNN算法中,所选择的邻居都是已经正确分类的对象。该方法在定类决策上只依据最邻近的一个或者几个样本的类别来决定待分样本所属的类别。

KNN 算法本身简单有效,它是一种 lazy-learning 算法,分类器不需要使用训练集进行训练,训练时间复杂度为0。KNN 分类的计算复杂度和训练集中的文档数目成正比,也就是说,如果训练集中文档总数为 n,那么 KNN 的分类时间复杂度为O(n)。

前面的例子中强调了选择合适的K值的重要性。如果太小,则最近邻分类器容易受到训练数据的噪声而产生的过分拟合的影响;相反,如果K太大,最近分类器可能会误会分类测试样例,因为最近邻列表中可能包含远离其近邻的数据点。(如下图所示)

Python K最近邻从原理到实现的方法 

K较大时的最近邻分类

可见,K值的选取还是非常关键。

2.算法算法描述

k近邻算法简单、直观:给定一个训练数据集(包括类别标签),对新的输入实例,在训练数据集中找到与该实例最邻近的k个实例,这k个实例的多数属于某个类,就把该输入实例分为这个类。下面是knn的算法步骤。

算法步骤如下所示:

Python K最近邻从原理到实现的方法

对每个测试样例z=(x′,y′),算法计算它和所有训练样例(x,y)属于D之间的距离(如欧氏距离,或相似度),以确定其最近邻列表Dz。如果训练样例的数目很大,那么这种计算的开销就会很大。不过,可以使索引技术降低为测试样例找最近邻是的计算量。

特征空间中两个实例点的距离是两个实例相似程度的反映。

一旦得到最近邻列表,测试样例就可以根据最近邻的多数类进行分类,使用多数表决方法。

K值选择

k值对模型的预测有着直接的影响,如果k值过小,预测结果对邻近的实例点非常敏感。如果邻近的实例恰巧是噪声数据,预测就会出错。也就是说,k值越小就意味着整个模型就变得越复杂,越容易发生过拟合。

相反,如果k值越大,有点是可以减少模型的预测误差,缺点是学习的近似误差会增大。会使得距离实例点较远的点也起作用,致使预测发生错误。同时,k值的增大意味着模型变得越来越简单。如果k=N,那么无论输入实例是什么,都将简单的把它预测为样本中最多的一类。这显然实不可取的。

在实际建模应用中,k值一般取一个较小的数值,通常采用cross-validation的方法来选择最优的k值。

3.K最邻近算法实现(Python)

KNN.py(代码来源《机器学习实战》一书)

from numpy import *
import operator

class KNN:
  def createDataset(self):
    group = array([[1.0,1.1],[1.0,1.0],[0,0],[0,0.1]])
    labels = ['A','A','B','B']
    return group,labels

  def KnnClassify(self,testX,trainX,labels,K):
    [N,M]=trainX.shape

  #calculate the distance between testX and other training samples
    difference = tile(testX,(N,1)) - trainX # tile for array and repeat for matrix in Python, == repmat in Matlab
    difference = difference ** 2 # take pow(difference,2)
    distance = difference.sum(1) # take the sum of difference from all dimensions
    distance = distance ** 0.5
    sortdiffidx = distance.argsort()

  # find the k nearest neighbours
    vote = {} #create the dictionary
    for i in range(K):
      ith_label = labels[sortdiffidx[i]];
      vote[ith_label] = vote.get(ith_label,0)+1 #get(ith_label,0) : if dictionary 'vote' exist key 'ith_label', return vote[ith_label]; else return 0
    sortedvote = sorted(vote.iteritems(),key = lambda x:x[1], reverse = True)
    # 'key = lambda x: x[1]' can be substituted by operator.itemgetter(1)
    return sortedvote[0][0]

k = KNN() #create KNN object
group,labels = k.createDataset()
cls = k.KnnClassify([0,0],group,labels,3)
print cls

运行:
1. 在Python Shell 中可以运行KNN.py

>>>import os
>>>os.chdir("/home/liudiwei/code/data_miningKNN/")
>>>execfile("KNN.py")

输出:B
(B表示类别)

2.或者terminal中直接运行

$ python KNN.py

3.也可以不在KNN.py中写输出,而选择在Shell中获得结果,i.e.,

>>>import KNN
>>> KNN.k.KnnClassify([0,0],KNN.group,KNN.labels,3)

附件(两张自己的计算过程图):

Python K最近邻从原理到实现的方法 

1 KNN算法核心部分

Python K最近邻从原理到实现的方法 

图2 KNN计算过程

说明:上述图片仅供参考,看不懂就自己测试一组数据如[0,1]慢慢推导一下吧

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

Python 相关文章推荐
Python pickle类库介绍(对象序列化和反序列化)
Nov 21 Python
如何在Python函数执行前后增加额外的行为
Oct 20 Python
Python通过Django实现用户注册和邮箱验证功能代码
Dec 11 Python
Python实现简易版的Web服务器(推荐)
Jan 29 Python
python调用OpenCV实现人脸识别功能
May 25 Python
python二维键值数组生成转json的例子
Dec 06 Python
python实现百度OCR图片识别过程解析
Jan 17 Python
python实现简单颜色识别程序
Feb 19 Python
jupyter notebook的安装与使用详解
May 18 Python
Python-openCV开运算实例
Jul 05 Python
django前端页面下拉选择框默认值设置方式
Aug 09 Python
python中pickle模块浅析
Dec 29 Python
Python数据可视化 pyecharts实现各种统计图表过程详解
Aug 15 #Python
浅谈Python 敏感词过滤的实现
Aug 15 #Python
pycharm创建scrapy项目教程及遇到的坑解析
Aug 15 #Python
通过selenium抓取某东的TT购买记录并分析趋势过程解析
Aug 15 #Python
Python依赖包整体迁移方法详解
Aug 15 #Python
使用python批量修改文件名的方法(视频合并时)
Mar 24 #Python
python 修改本地网络配置的方法
Aug 14 #Python
You might like
PHP Ajax实现页面无刷新发表评论
2007/01/02 PHP
php缓冲 output_buffering和ob_start使用介绍
2014/01/30 PHP
C# WinForm中实现快捷键自定义设置实例
2015/01/23 PHP
php中file_exists函数使用详解
2015/05/08 PHP
alixixi runcode.asp的代码不错的应用
2007/08/08 Javascript
niceTitle 基于jquery的超链接提示插件
2010/05/31 Javascript
使用js判断TextBox控件值改变然后出发事件
2014/03/07 Javascript
javascript实现的平方米、亩、公顷单位换算小程序
2014/08/11 Javascript
js使用正则实现ReplaceAll全部替换的方法
2014/08/22 Javascript
浅谈JS函数定义方式的区别
2016/10/30 Javascript
微信小程序 点击控件后选中其它反选实例详解
2017/02/21 Javascript
Vue使用高德地图搭建实时公交应用功能(地图 + 附近站点+线路详情 + 输入提示+换乘详情)
2018/05/16 Javascript
jQuery实现的点击按钮改变样式功能示例
2018/07/21 jQuery
node.js事件轮询机制原理知识点
2019/12/22 Javascript
十分钟教你上手ES2020新特性
2020/02/12 Javascript
解决Ant Design Modal内嵌Form表单initialValue值不动态更新问题
2020/10/29 Javascript
Python实现的检测网站挂马程序
2014/11/30 Python
python控制windows剪贴板,向剪贴板中写入图片的实例
2018/05/31 Python
Python for i in range ()用法详解
2020/09/18 Python
Python3变量与基本数据类型用法实例分析
2020/02/14 Python
Python如何用filter函数筛选数据
2020/03/05 Python
Python requests及aiohttp速度对比代码实例
2020/07/16 Python
CSS3属性使网站设计增强同时不消弱可用性
2009/08/29 HTML / CSS
css3 中的新特性加强记忆详解
2016/04/16 HTML / CSS
CSS3,线性渐变(linear-gradient)的使用总结
2017/01/09 HTML / CSS
html5 canvas fillRect坐标和大小的问题解决方法
2014/03/26 HTML / CSS
html5开发三八女王节表白神器
2018/03/07 HTML / CSS
日本运动品牌美津浓官方购物网站:MIZUNO SHOP
2016/08/21 全球购物
幼儿园大班新学期寄语
2014/01/18 职场文书
C++程序员求职信范文
2014/04/14 职场文书
关于教师节的广播稿
2014/09/10 职场文书
小学运动会开幕词
2015/01/28 职场文书
运动会闭幕式致辞
2015/07/29 职场文书
2015年大学组织委员个人工作总结
2015/10/23 职场文书
火锅店的开业营销方案范本!
2019/07/05 职场文书
OpenCV-Python实现怀旧滤镜与连环画滤镜
2021/06/09 Python