1.算法思想
首先用一个实际的例子来说明:
如下图,绿色圆要被决定赋予哪个类,是红色三角形还是蓝色四方形?如果K=3,由于红色三角形所占比例为2/3,绿色圆将被赋予红色三角形那个类,如果K=5,由于蓝色四方形比例为3/5,因此绿色圆被赋予蓝色四方形类。
如果一个样本在特征空间中的k个最相似(即特征空间中最邻近)的样本中的大多数属于某一个类别,则该样本也属于这个类别。KNN算法中,所选择的邻居都是已经正确分类的对象。该方法在定类决策上只依据最邻近的一个或者几个样本的类别来决定待分样本所属的类别。
其算法的描述为:
1)计算测试数据与各个训练数据之间的距离;
2)按照距离的递增关系进行排序;
3)选取距离最小的K个点;
4)确定前K个点所在类别的出现频率;
5)返回前K个点中出现频率最高的类别作为测试数据的预测分类。
2.K近邻用于回归
由前面的定义可以知道,KNN在这里被当作了一种分类算法,但是KNN是可以用来进行回归的。但是,怎么将KNN 算法用于回归呢?其实大致的步骤是一样的,也是对新来的预测实例寻找 K 近邻,然后对这 K 个样本的目标值取均值即可作为新样本的预测值。
3.用sklearn来实现KNN回归
# -*- coding: utf-8 -*-
"""
@author: Haojie Shu
@time:2019/09/17
@description:KNN用于回归
"""
import numpy as np
import matplotlib.pyplot as plt
from sklearn import neighbors
np.random.seed(0)
X = np.sort(5 * np.random.rand(40, 1), axis=0)
T = np.linspace(0, 5, 500)[:, np.newaxis]
y = np.sin(X).ravel()
y[::5] += 1 * (0.5 - np.random.rand(8))
n_neighbors = 5
for i, weights in enumerate(['uniform', 'distance']):
knn = neighbors.KNeighborsRegressor(n_neighbors, weights=weights)
y_ = knn.fit(X, y).predict(T)
plt.subplot(2, 1, i+1)
plt.scatter(X, y, c='k', label='data')
plt.plot(T, y_, c='g', label='prediction')
plt.axis('tight')
plt.legend()
plt.title("KNeighborsRegressor (k = %i, weights = '%s')" % (n_neighbors, weights))
plt.tight_layout()
plt.show()
得到的图
这里的代码不是特别的复杂,需要弄清楚以下两点:
(1)knn-regression是怎么进行预测的,这里的问题是我们并不知道y的坐标在哪里,而是要求这个y坐标,既然y坐标不确定,怎么找他的k近邻?查看我在stack和知乎的提问:stack的回答,通过找和
x坐标最近的来得到的,他的近邻就是x坐标最近的近邻
(2)注意,上面这两幅图有什么不一样,第一个是weights=’uniform’,也就是将所有的y坐标加起来求平均,就是预测的y坐标。而weights=’distance’的效果则是根据距离来确定权重,距离越近,权重越大。