python机器学习API引见12: K近邻算法——KNeighborsClassifier
作者头像
  • 陈丽慧
  • 2019-12-10 07:21:40 7

K近邻算法(K-Nearest Neighbor,KNN)是最简单的机器学习算法之一,易于理解和实现。它主要用于分类和回归任务。KNN的输入是实例的特征向量,通过计算新数据与已有数据特征值之间的距离,选取K(K≥1)个最近的邻居进行分类或回归判断。如果K=1,新数据会被直接分配给最近的邻居。

分类任务

在分类任务中,输入的是实例的类别。对于新的实例,根据其K个最近邻的训练实例类别,采用多数表决的方式进行预测。

回归任务

在回归任务中,输入的是实例的数值。对于新的实例,取其K个最近邻的训练实例数值的平均值作为预测值。

KNN算法没有显式的训练过程,而是直接进行预测。实际上,它利用训练数据集对特征空间进行划分,并将这种划分作为模型的一部分。

KNN算法的关键要素

KNN算法包含三个关键要素:K值的选择、距离度量以及分类决策规则。K值越小,模型越复杂,但可能过拟合;K值越大,模型越简单,但可能会忽略局部细节。常用的距离度量方法是欧氏距离。分类决策规则通常包括权重分配,其中均匀权重(uniform)和距离权重(distance)是最常见的两种方法。在实际应用中,通常通过交叉验证来确定最优的K值。

kd树的应用

KNN算法在处理大量训练数据时,线性扫描方法效率较低。因此,引入kd树来加速搜索过程。kd树是一种二叉树结构,通过递归分割空间来构建。kd树的构建步骤包括创建根节点、不断切分域直至所有节点的子域中没有样本为止。

KNeighborsClassifier函数详解

KNeighborsClassifier类提供了多种参数来定制KNN算法的行为。以下是主要参数及其说明:

  • n_neighbors:指定K值。
  • weights:指定投票权重类型,可以是“uniform”(所有邻居权重相同)或“distance”(权重与距离成反比),也可以自定义函数。
  • algorithm:指定计算最近邻的方法,可选“balltree”、“kdtree”、“brute”或“auto”。
  • leafsize:指定BallTree或kdtree节点的大小,影响构建时间和查询速度。
  • metric:指定距离度量方法,默认为Minkowski距离。
  • p:在Minkowski度量中的指数,p=1对应曼哈顿距离,p=2对应欧氏距离。
  • n_jobs:并行处理的设置,-1表示使用所有可用的CPU核心。

KNeighborsClassifier的方法

  • fit(x, y):训练模型。
  • predict(x):用模型进行预测。
  • score(x, y[, sample_weight]):返回模型的预测性能评分。
  • predict_proba(x):返回每个类别的概率值。
  • kneighbors(x, nneighbors, returndistance):返回样本的K个最近邻点。
  • kneighborsgraph(x, nneighbors, mode):返回样本点的连接图。

示例代码

以下是一些示例代码,演示如何使用KNeighborsClassifier进行分类和评估。

```python from sklearn.datasets import loaddigits from sklearn.modelselection import traintestsplit import numpy as np import matplotlib.pyplot as plt

加载数据

def loaddigitsdata(): digits = loaddigits() # 分层采样 return traintestsplit(digits.data, digits.target, testsize=0.25, random_state=0, stratify=digits.target)

训练模型

def testKNerghborsClassifier(xtrain, xtest, ytrain, ytest): cls = KNeighborsClassifier() cls.fit(xtrain, ytrain) print("KNerghbors training score set is: {:.3f}".format(cls.score(xtrain, ytrain))) print("KNerghbors test score set is: {:.3f}".format(cls.score(xtest, y_test)))

不同权重对预测效果的影响

def testKNeighborsClassifierkw(xtrain, xtest, ytrain, ytest): ks = np.linspace(1, ytrain.size, num=100, endpoint=False, dtype='int') weights = ['uniform', 'distance'] fig, ax = plt.subplots() for weight in weights: trainingscores = [] testingscores = [] for k in ks: cls = KNeighborsClassifier(weights=weight, nneighbors=k) cls.fit(xtrain, ytrain) trainingscores.append(cls.score(xtrain, ytrain)) testingscores.append(cls.score(xtest, ytest)) ax.plot(ks, trainingscores, label=f"KNeighbors training score: weight={weight}") ax.plot(ks, testingscores, label=f"KNeighbors test score: weight={weight}") ax.legend(loc='best') ax.setxlabel("K value") ax.setylabel("score value") ax.setylim(0, 1.05) ax.set_title("KNeighbors") plt.show()

不同p值对预测效果的影响

def testKNeighborsClassifierkp(xtrain, xtest, ytrain, ytest): ks = np.linspace(1, ytrain.size, num=100, endpoint=False, dtype='int') ps = [1, 2, 8] fig, ax = plt.subplots() for p in ps: trainingscores = [] testingscores = [] for k in ks: cls = KNeighborsClassifier(p=p, nneighbors=k) cls.fit(xtrain, ytrain) trainingscores.append(cls.score(xtrain, ytrain)) testingscores.append(cls.score(xtest, ytest)) ax.plot(ks, trainingscores, label=f"KNeighbors training score: p={p}") ax.plot(ks, testingscores, label=f"KNeighbors test score: p={p}") ax.legend(loc='best') ax.setxlabel("K value") ax.setylabel("score value") ax.setylim(0, 1.05) ax.set_title("KNeighbors") plt.show()

xtrain, xtest, ytrain, ytest = loaddigitsdata() testKNerghborsClassifier(xtrain, xtest, ytrain, ytest) testKNeighborsClassifierkw(xtrain, xtest, ytrain, ytest) testKNeighborsClassifierkp(xtrain, xtest, ytrain, y_test) ```

结果分析

通过上述实验可以看出,权重参数(uniform 和 distance)对预测效果有显著影响。均匀权重在K值较大时,预测效果较为稳定,而距离权重则在K值较小时表现更好。参数p值的变化对预测效果的影响较小,这表明曼哈顿距离和欧氏距离对分类器的预测效果影响不大。

    本文来源:图灵汇
责任编辑: : 陈丽慧
声明:本文系图灵汇原创稿件,版权属图灵汇所有,未经授权不得转载,已经协议授权的媒体下载使用时须注明"稿件来源:图灵汇",违者将依法追究责任。
    分享
引见近邻KNeighborsClassi算法机器python学习fierAPI12
    下一篇