k-近邻算法是分类算法中的入门算法,它的原理是:存在一个数据集合,并且集合中的每个数据都存在标签。输入没有标签的新数据时,将新数据的每个特征与样本集合数据对应的特征进行比较,然后算法提取数据集中特征最相似数据的分类标签。通常k取不大于20的奇数,出现次数最多的分类就是新数据的分类。
伪代码如下:
- 计算已知类别数据集中的点与当前点之间的距离;
- 按照距离递增次序排序;
- 选取与当前距离最小的k个点;
- 确定前k个点所在类别的出现频率;
- 返回前k个点频率最高的类别作为当前点的预测分类。
简单实例
[d = sqrt{(xA_{0}-xB_{0})^{2} + (xA_{1}-xB_{1})^{2}}
]
代码实现
import numpy as np
import operator
def createDataSet():
'''
生成数据集
:return:特征矩阵 标签
'''
group = np.array([[1.0, 1.1], [1.0, 1.0], [0, 0], [0, 0.1]])
labels = np.array(['A', 'A', 'B', 'B'])
return group, labels
def classify0(inX, dataSet, labels, k):
'''
k近邻算法
:param inX: 新数据特征
:param dataSet: 数据特征矩阵
:param labels: 数据标签
:param k: k值
:return:分类结果
'''
# 计算欧式距离
# np.tile(A,n),功能是将数组A重复n次,构成一个新的数组
# np.argsort 返回数组值从小到大的索引值
dataSetSize = dataSet.shape[0]
diffMat = np.tile(inX, (dataSetSize, 1)) - dataSet
sqDiffMat = diffMat**2
sqDistances = sqDiffMat.sum(axis=1)
distances = sqDistances**0.5
sortedDistIndicies = np.argsort(distances)
# print(sortedDistIndicies) [2 3 1 0]
# 选择距离最小的k个点
classCount = {}
for i in range(k):
voteILabel = labels[sortedDistIndicies[i]]
classCount[voteILabel] = classCount.get(voteILabel, 0) + 1
# print(classCount) {'B': 2, 'A': 1}
# 排序
# sorted(iterable, key=None, reverse=False)
sortedClassCount = sorted(classCount.items(), key=lambda x:x[1], reverse=True)
return sortedClassCount[0][0]
if __name__ == '__main__':
group, labels = createDataSet();
pred = classify0([0, 0], group, labels, 3)
print(pred)