在前两篇文章机器学习实战-2-KNN和机器学习实战-3-基于KNN的约会网站配对实现中结合实际案例详细讲解了KNN算法的知识,主要包含:
还有其他的内容,比如KNN算法中使用的欧式距离涉及到的机器学习中的度量问题、jupyter notebook中如何使用KNN算法等。本文主要是对KNN算法做一个总结。
KNN算法 | |
---|---|
功能 | 分类(核心),回归 |
算法类型 | 有监督学习-惰性学习 |
数据输入 | 特征矩阵至少包含k个训练样本,数据标签特征空间中的各个特征的量纲需要统一,如果不统一,需要做归一化处理自定义的的超参数k |
数据输出 | KNN分类:输出的是标签中的某个类别KNN回归:输出的是对象的属性值,该值是距离输入的数据最近的k个训练样本标签的均值 |
k
个点;k
个点所在类别的出现频率;k
个点所出现频率最高的类别作为当前点的预测分类。利用Python创建一个KNN分类器:
import numpy as np
"""
函数说明:KNN算法分类
函数参数:
inX 用于分类的数据集(测试集)
dataSet 用于训练的数据(训练集)
labels 分类标签
k 算法参数,选择距离最近的k个点
修改时间:
2021-02-28
"""
def classify0(inX, dataSet, labels, k):
dataSetSize = dataSet.shape[0] # 文件行数,即大小
diffMat = np.tile(inX, (dataSetSize, 1)) - dataSet # np.tile表示在两个方向上的重复次数,达到和原始数据相同的shape,以便能够相减
sqDiffMat = diffMat ** 2
sqDistances = sqDiffMat.sum(axis=1)
distances = sqDistances ** 0.5 # 以上3步:距离相减再平方,再求和,再开根号
# 获取到的是索引值!!!
sortedDistIndices = distances.argsort() # 全部距离从小到大排序后的索引值
classCount = {} # 存储类别次数的字典
for i in range(k):
voteIlabel = labels[sortedDistIndices[i]] # 根绝每个索引,取出对应的前k个元素的类别
classCount[voteIlabel] = classCount.get(voteIlabel,0) + 1 # 计算类别次数;get方法返回指定键的值,否则返回默认值
# python3中使用item()
# reverse表示降序排序字典
# key=operator.itemgetter(0)表示根据字典的键进行排序
# key=operator.itemgetter(1)表示根据字典的值进行排序
sortedClassCount = sorted(classCount.items(), key=operator.itemgetter(1),reverse=True)
return sortedClassCount[0][0] # 返回次数最多的类别,即所要分类的类别
根据电影分类问题写出的简洁版本:
import pandas as pd
"""
函数功能:KNN分类器
参数说明:
inX:待预测分类的数据
dataSet:原数据集,训练集
k:k-近邻算法中的超参数k
返回值:
分类结果
修改时间:
2021-02-28
"""
def classify0(inX, dataSet,k):
result = []
# 1、求新数据和每个原数据的距离
dist = list(((data.iloc[:6,1:3] - new_data) ** 2).sum(1) ** 0.5)
# 2、将求出的距离和电影标签放在一起
dist_labels = pd.DataFrame({"dist":dist,"labels":data["电影类型"].tolist()})
# 3、根据距离升序排列,取出前k个
dist_sorted = dist_labels.sort_values(by="dist")[:k]
# 4、排序之后取出标签,并统计频数
res = dist_sorted.loc[:,"labels"].value_counts()
result.append(res.index[0])
return result
1、《机器学习实战》一书
2、李航老师:《统计学习方法》