knn分类算法(鸢尾花数据集实现)
1、题目:使用鸢尾花数据集,实现knn算法
这是python机器学习基础教程中第一章1.7部分的
2、算法设计
(一)knn算法概述
邻近算法,或者说K最近邻(kNN,k-NearestNeighbor)分类算法是数据挖掘分类技术中最简单的方法之一。所谓K最近邻,就是k个最近的邻居的意思,说的是每个样本都可以用它最接近的k个邻居来代表。Cover和Hart在1968年提出了最初的邻近算法。KNN是一种分类(classification)算法,它输入基于实例的学习(instance-based learning),属于懒惰学习(lazy learning)即KNN没有显式的学习过程,也就是说没有训练阶段,数据集事先已有了分类和特征值,待收到新样本后直接进行处理。与急切学习(eager learning)相对应。KNN是通过测量不同特征值之间的距离进行分类。 思路是:如果一个样本在特征空间中的k个最邻近的样本中的大多数属于某一个类别,则该样本也划分为这个类别。KNN算法中,所选择的邻居都是已经正确分类的对象。该方法在定类决策上只依据最邻近的一个或者几个样本的类别来决定待分样本所属的类别。提到KNN,网上最常见的就是下面这个图,可以帮助大家理解。我们要确定绿点属于哪个颜色(红色或者蓝色),要做的就是选出距离目标点距离最近的k个点,看这k个点的大多数颜色是什么颜色。当k取3的时候,我们可以看出距离最近的三个,分别是红色、红色、蓝色,因此得到目标点为红色。
(二)knn算法描述
1)计算测试数据与各个训练数据之间的距离;
2)按照距离的递增关系进行排序;
3)选取距离最小的K个点;
4)确定前K个点所在类别的出现频率;
5)返回前K个点中出现频率最高的类别作为测试数据的预测分类
(三)鸢尾花数据集
在Sklearn机器学习包中,集成了各种各样的数据集,包括前面的糖尿病数据集,这里引入的是鸢尾花卉(Iris)数据集,它是很常用的一个数据集。鸢尾花有三个亚属,分别是山鸢尾(Iris-setosa)、变色鸢尾(Iris-versicolor)和维吉尼亚鸢尾(Iris-virginica)。该数据集一共包含4个特征变量,1个类别变量。共有150个样本,iris是鸢尾植物,这里存储了其萼片和花瓣的长宽,共4个属性,鸢尾植物分三类。iris里有两个属性iris.data,iris.target。data是一个矩阵,每一列代表了萼片或花瓣的长宽,一共4列,每一行代表某个被测量的鸢尾植物,一共采样了150条记录。target是一个数组,存储了data中每条记录属于哪一类鸢尾植物,所以数组的长度是150,数组元素的值因为共有3类鸢尾植物,所以不同值只有3个。种类为山鸢尾、杂色鸢尾、维吉尼亚鸢尾。
3、源代码
import numpy as np
from sklearn.datasets import load_iris
from sklearn.model_selection import train_test_split
import operator as opt
import matplotlib.pyplot as plt
from sklearn.datasets import load_iris
iris_dataset = load_iris()
from sklearn.model_selection import train_test_split
X_train,X_test,y_train,y_test = train_test_split(
iris_dataset['data'],iris_dataset['target'],random_state=0)
def knn(dataSet,labels,testData, k):
distSquareMat = (dataSet - testData) ** 2 #计算差值的平方
distSquareSums = distSquareMat.sum(axis=1) #求每一行的差值平方和
distances = distSquareSums ** 0.5 #开根号,得出每个样本到测试点的距离
sortedIndices = distances.argsort() #排序,得到排序后的下标
indices = sortedIndices[:k] #取最小的k个
labelCount = {} #存储每个label的出现次数
for i in indices:
label = labels[i]
labelCount[label] = labelCount.get(label, 0) + 1 #次数加一
sortedCount = sorted(labelCount.items(), key=opt.itemgetter(1), reverse=True) #对label出现的次数从大到小进行排序
return sortedCount[0][0] #返回出现次数最大的label
dataSet = iris_dataset.data
labels = iris_dataset.target
testData = np.array([[5,2.9,1,0.2]])
k = 3
outputLabel = knn(dataSet,labels,testData,k)
print("Your input is:", testData, "and classified to class: ", outputLabel)
4、测试用例设计及调试过程截屏
5、经验总结
(一)Knn算法优缺点
knn算法理论成熟,思想简单,既可以用来做分类又可以做回归,可以用于非线性分类且训练时间复杂度比支持向量机之类的算法低,对数据没有假设,准确度高,对异常点不敏感。由于knn方法主要靠周围有限的邻近的样本,而不是靠判别类域的方法来确定所属的类别,因此对于类域的交叉或重叠较多的待分类样本集来说,knn方法较其他方法更为适合。该算法比较适用于样本容量比较大的类域的自动分类,而那些样本容量比较小的类域采用这种算法比较容易产生误分类情况。但计算量大,尤其是特征数非常多的时候,.样本不平衡的时候,对稀有类别的预测准确率低。
(二)自我总结
本次作业,参考了网络博客,自己对于knn算法的认识比较浅显,无法独立完成knn算法设计,且在参考下只能简单实现knn算法,但认识了knn算法的主要理论及思想,掌握了在sklearn直接调用成熟knn算法的方法。
(三)参考博客:https://blog.csdn.net/jiangsujiangjiang/article/details/80568196
https://www.cnblogs.com/deadwood-2016/p/8087337.html