「作者主页」:士别三日wyx
「作者简介」:CSDN top100、阿里云博客专家、华为云享专家、网络安全领域优质创作者
「推荐专栏」:零基础快速入门人工智能《机器学习入门到精通》
K-近邻算法的K是指邻居的个数,「K值」不同,算法的「准确率」也不同,我们需要不断调整K值,以提高算法的准确率。在「调整」过程中,我们需要用到「交叉验证」。
交叉验证(Cross-Validation)是在机器学习建立模型和验证模型「参数」时常用的方法,用于「评估」机器模型的性能指标,从而进行「模型选择」。
交叉验证的「基本思想」是,把原始数据分组,一部分当做训练集,另一部分作为验证集,先用训练集对算法模型进行训练,再用验证集测试训练得到的算法模型。
比如,把数据分成四份,先用第一份数据当验证集,把后面三份的训练结果与第一份做验证;再用第二份数据当验证集,把其他三份数据的训练结果和第二份做验证;以此类推。。。
交叉验证常配合网格搜索一同使用。
网格搜索也叫超「参数搜索」,比如K-近邻算法的K值需要手动指定参数,这种参数就叫超参数。网格搜索通过预设几组超参数组合,每组超参数都用交叉验证进行评估,从而选出「最优」的参数组合来建立模型。
sklearn 模块 GridSearchCV 很好的实现了网格搜索,它可以自动调参,只要把参数输进去,就能给出最优的结果和参数。
sklearn.model_selection.GridSearchCV( estimator,param_grid,cv)
{ "n_neighbors": [1, 3, 5] , }
返回值属性
接下来,我们使用 GridSearchCV 来选择 K-近邻算法的「最佳K值」
使用 sklearn 自带的的鸢尾花「数据集」,数据集划分为60%训练,40%测试。
from sklearn import datasets
from sklearn import model_selection
# 1、获取数据集
iris = datasets.load_iris()
# 2、划分数据集
# x_train:训练集特征,x_test:测试集特征,y_train:训练集目标,y_test:测试集目标
x_train, x_test, y_train, y_test = model_selection.train_test_split(iris.data, iris.target, random_state=6)
print('训练集特征:', len(x_train))
print('测试集特征:', len(x_test))
print('训练集目标:', len(y_train))
print('测试集特征:', len(y_test))
输出:
训练集特征: 112
测试集特征: 38
训练集目标: 112
测试集特征: 38
从输出结果可以看到,训练集和测试集的比例符合预期
接下来,对训练集特征和测试集特征进行「标准化」处理
from sklearn import datasets
from sklearn import model_selection
from sklearn import preprocessing
# 1、获取数据集
iris = datasets.load_iris()
# 2、划分数据集
# x_train:训练集特征,x_test:测试集特征,y_train:训练集目标,y_test:测试集目标
x_train, x_test, y_train, y_test = model_selection.train_test_split(iris.data, iris.target, random_state=6)
# 3、特征标准化
ss = preprocessing.StandardScaler()
x_train = ss.fit_transform(x_train)
x_test = ss.fit_transform(x_test)
print(x_train)
输出:
[[-0.18295405 -0.192639 0.25280554 -0.00578113]
[-1.02176094 0.51091214 -1.32647368 -1.30075363]
[-0.90193138 0.97994624 -1.32647368 -1.17125638]
从输出结果可以看到,特征已经标准化。
将训练特征集和测试特征集传给KNN,并查看「准确率」。
from sklearn import datasets
from sklearn import model_selection
from sklearn import preprocessing
from sklearn import neighbors
# 1、获取数据集
iris = datasets.load_iris()
# 2、划分数据集
# x_train:训练集特征,x_test:测试集特征,y_train:训练集目标,y_test:测试集目标
x_train, x_test, y_train, y_test = model_selection.train_test_split(iris.data, iris.target, random_state=6)
# 3、特征标准化
ss = preprocessing.StandardScaler()
x_train = ss.fit_transform(x_train)
x_test = ss.fit_transform(x_test)
# 4、KNN算法处理
knn = neighbors.KNeighborsClassifier(n_neighbors=2)
knn.fit(x_train, y_train)
print(knn.score(x_test, y_test))
输出:
0.8947368421052632
从输出结果可以看到,准确率是89%,一般般。
将不同的K值封装成字典,传给 GridSearchCV,计算「最优」的参数。
from sklearn import datasets
from sklearn import model_selection
from sklearn import preprocessing
from sklearn import neighbors
# 1、获取数据集
iris = datasets.load_iris()
# 2、划分数据集
# x_train:训练集特征,x_test:测试集特征,y_train:训练集目标,y_test:测试集目标
x_train, x_test, y_train, y_test = model_selection.train_test_split(iris.data, iris.target, random_state=6)
# 3、特征标准化
ss = preprocessing.StandardScaler()
x_train = ss.fit_transform(x_train)
x_test = ss.fit_transform(x_test)
# 4、KNN算法处理
knn = neighbors.KNeighborsClassifier(n_neighbors=2)
# 5、参数调优
params = {"n_neighbors": [1, 3, 5, 7]}
knn = model_selection.GridSearchCV(knn, param_grid=params, cv=10)
knn.fit(x_train, y_train)
print('最优参数:', knn.best_params_)
print('最优准确率:', knn.best_score_)
print('最优分类器:', knn.best_estimator_)
输出:
最优参数: {'n_neighbors': 5}
最优准确率: 0.9727272727272729
最优分类器: KNeighborsClassifier()
从输出结果可以看到,最优的K值参数是5,准确率达到了97%