【统计学习】K-Nearest Neighbors(KNN)
算法实现
1.算出输入点与每个点的距离
2.对距离排序
3.选出最邻近K个点进行投票
4.分到投票数最多的类
算法详解
K最邻近分类模型属于“基于记忆”的非参数局部模型,这种模型并不是立即利用训练数据建立模型,数据也不再被函数和参数所替代。在对测试样例进行类别预测的时候,找出和其距离最接近的K个样例,以其中数量最多的类别作为该样例的类预测结果。
其属于生成模型
K 值会对算法的结果产生重大影响。K值较小意味着只有与输入实例较近的训练实例才会对预测结果起作用,容易发生过拟合;如果 K 值较大,优点是可以减少学习的估计误差,缺点是学习的近似误差增大,这时与输入实例较远的训练实例也会对预测起作用,是预测发生错误。在实际应用中,K 值一般选择一个较小的数值,通常采用交叉验证的方法来选择最有的 K 值。随着训练实例数目趋向于无穷和 K=1 时,误差率不会超过贝叶斯误差率的2倍,如果K也趋向于无穷,则误差率趋向于贝叶斯误差率。

$L_d$距离就是相减d次方和再开d次方
[以下内容转于https://zhuanlan.zhihu.com/p/25994179]



数据的归一化很重要
Code

import numpy as np;
import seaborn as sns
import math
import pandas as pd
import matplotlib.pyplot as plt
#距离计算函数
def ComputeEuclideanDistance(x,y):
tx=np.matrix(x).T
ty=np.matrix(y).T
return math.sqrt((tx-ty).T*(tx-ty))
#获取K个近邻点
def getNeighbors(dataset,curx, k):
neighbors=[]
x_withdis=[]
for d in dataset:
#print(d)
x_withdis.append( [d[0,0] ,d[0,1],d[0,2] , (ComputeEuclideanDistance(d[:, [0, 1]], curx))] )
x_withdis=np.array(x_withdis)
sarg=np.argsort(x_withdis[:,3]) #对距离排序
#print(np.matrix(x_withdis[sarg]))
for a in range(k):
neighbors.append(x_withdis[sarg[a]])
return np.matrix(neighbors)
#生成两个满足高斯分布的数据集
c=[]
x1=np.random.normal(1,10,100)
y1=np.random.normal(1,10,100)
x2=np.random.normal(12,5,100)
y2=np.random.normal(12,5,100)
for i in range(100):
c.append([x1[i],y1[i],0])
c.append([x2[i],y2[i],1])
c=np.matrix(c)
#print(c)
plt.scatter(x1,y1)
plt.scatter(x2,y2)
verge=[]
for r in np.arange(-24,24,0.5):
for j in np.arange(-24,30,0.5):
n = getNeighbors(c, [r, j], 5)
c_0 = 0
c_1 = 0
#投票
for i in n:
if (i[0, 2] == 1):
c_1 = c_1 + 1
else:
c_0 = c_0 + 1
if (abs(c_0-c_1)<=1):
verge.append([r,j])
#print([r,j,0])
#plt.scatter(r,j,marker='x',c='b')
print(r)
verge=np.matrix(verge)
plt.plot(verge[:,0],verge[:,1])
plt.show()