KNN算法详解及实现

本文仅供自己学习所用~

参考博客:http://t.csdn.cn/1IB1Z(什么是KNN算法?)

                  http://t.csdn.cn/sSN3U(鸢尾花数据集实现KNN算法)


前言

#杭电极客深度学习考核作业Ⅰ

菜鸡一枚,第一次写博客,由此开启我的博客之路!

一、KNN是什么?

KNN(K-Nearest Neighbor)算法是机器学习算法中最基础、最简单的算法之一。它既能用于分类,也能用于回归。KNN通过测量不同特征值之间的距离来进行分类。

KNN算法思想:(简单来说)当预测一个新的值x的时候,根据它距离最近的K个点是什么类别来判断x属于哪个类别

在这里插入图片描述

从图中我们容易知道,绿色点所在的内圆中有两红一蓝,那么根据KNN算法“物以类聚,人以群分”的思想来判断,绿点点应该被分为红色三角形一类。到这里,你就基本了解了著名的KNN算法是干什么用的了。

二、KNN用法分析

k近邻法三要素:距离度量k值的选择分类决策规则


距离度量:

Lp​(xi​,xj​)=(∑i=1n​∣∣∣​xi(i)​−xj(l)​∣∣∣​p)p1​

p=1 曼哈顿距离
p = 2  欧氏距离
p = ∞  切比雪夫距离

常用欧氏距离


k值的选择:

k值小时,k近邻模型更复杂,容易发生过拟合;k值大时,k近邻模型更简单,又容易欠拟合。

在实践中,一般采用交叉验证的方式选取k值。

交叉验证的基本想法是重复地使用数据,把给定的数据进行切分,将切分的数据组合为训练集与测试集,在此基础上反复进行训练测试以及模型的选择。

交叉验证主要有三种方法:简单交叉验证(HoldOut检验)、k折交叉验证(k-fold交叉验证)、自助法。实现过程中用sklearn.model_selection.cross_val_score()实现交叉验证选取k值。

cross_val_score参数设置

#  cross_val_score参数设置
sklearn.model_selection.cross_val_score(estimator, # 需要使用交叉验证的算法
                                        X, # 输入样本数据
                                        y=None,  # 样本标签
                                        groups=None, # 将数据集分割为训练/测试集时使用的样本的组标签(一般用不到)
                                        scoring=None, # 交叉验证选择不同的评价方法
                                        cv=’warn’, # 交叉验证折数或可迭代的次数
                                        n_jobs=None, # 同时工作的cpu个数(-1代表全部)
                                        verbose=0, # 详细程度
                                        fit_params=None, # 传递给估计器(验证算法)的拟合方法的参数
                                        pre_dispatch=‘2*n_jobs’, # 控制并行执行期间调度的作业数量
                                        error_score=’raise-deprecating’) # 如果在估计器拟合中发生错误,要分配给该分数的值

cross_val_score的使用:(交叉验证发选取最佳k值的应用)

from sklearn.datasets import load_iris
from sklearn.model_selection import cross_val_score
import matplotlib.pyplot as plt
from sklearn.neighbors import KNeighborsClassifier

#加载鸢尾花数据集
iris = load_iris()
x = iris.data
y = iris.target
k_range = range(1, 31) # 设置循环次数
k_error = []
#循环,取k从1~30,查看误差效果
for k in k_range:
    knn = KNeighborsClassifier(n_neighbors=k)
    # KNeighborsClassifier是实现k近邻算法的一个类,n_neighbors:选取最近的点的个数为k
    scores = cross_val_score(knn, x, y, cv=6, scoring='accuracy')
                                        # cv参数决定数据集划分比例,这里是按照5:1划分训练集和测试集
    k_error.append(1 - scores.mean())

#画图,x轴为k值,y值为误差值,误差值越小越好
plt.plot(k_range, k_error)
plt.xlabel('Value of K in KNN')
plt.ylabel('Error')
plt.show()

结果如下:

由图知,该数据集在k=11时损失最小,因此接下来我们选择k=11进行训练


 类决策规则:

分类决策规则往往是多数表决,即由输入实例的k kk个邻近输入实例中的多数类决定输入实例的类。

三、KNN实例

代码如下:

import numpy as np
import matplotlib.pyplot as plt
from matplotlib.colors import ListedColormap
from sklearn import neighbors, datasets

n_neighbors = 11 # 由上面交叉验证得到的最佳k值

# 加载鸢尾花数据集
iris = datasets.load_iris()
# 选择其中的两个特征
X = iris.data[:, :2]
y = iris.target

h = .02 # 网格步长

# 创建色彩图, ListedColormap为mapplotlib.colors的一个类
cmap_light = ListedColormap(['LightPink', 'Lavender', 'Blue']) # 背景颜色(浅)
cmap_bold = ListedColormap(['DeepPink', 'BlueViolet', 'DeepSkyBlue']) # 点的颜色(深)

# 在两种权重下绘制图像
for weights in ['uniform', 'distance']:# 用于指定邻近样本的投票权重,“uniform”表示所有样本投票权重一致,如果为“distance”则表示投票权重与距离成反比
	# 创建knn分类器实例, 并进行训练拟合
	clf = neighbors.KNeighborsClassifier(n_neighbors, weights = weights)
    
	clf.fit(X,y) # 用训练数据拟合分类器模型

	 # 绘制决策边界
	x_min, x_max = X[:,0].min() - 1, X[:,0].max() + 1
	y_min, y_max = X[:,1].min() - 1, X[:,1].max() + 1
	xx, yy = np.meshgrid(np.arange(x_min, x_max, h),
						 np.arange(y_min, y_max, h))
	Z = clf.predict(np.c_[xx.ravel(), yy.ravel()]) # clf.predict用训练好的分类器去预测, a.ravel()将数组维度拉成一维数组
	
	Z = Z.reshape(xx.shape)
	plt.figure()
	plt.pcolormesh(xx, yy, Z, cmap = cmap_light) # 数据的分类显示(根据背景的三种颜色)

	# 绘制训练点
	plt.scatter(X[:, 0], X[:, 1], c = y, cmap = cmap_bold, edgecolor='k', s=20)
	plt.xlim(xx.min(), xx.max())
	plt.ylim(yy.min(), yy.max())
	plt.title('3-Class classification (k = %i, weights = "%s")' % (n_neighbors, weights))

plt.show()

输出如下:

"uniform"表示所有样本投票权重一致

“distance”则表示投票权重与距离成反比


总结

KNN有着非常明显的优点和缺点:

优点:精度高、对异常值不敏感、无数据输入假定

缺点:计算复杂度高、空间复杂度高,对内存要求较高,因为该算法存储了所有训练数据

适用数据范围:数值型和标称型

  • 1
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值