2-04-模型选择与调优

导入

在KNN算法中,k值的选择对我们最终的预测结果有着很大的影响

那么有没有好的方法能够帮助我们选择好的k值呢?

模型选择与调优

学习目标

2-04-模型选择与调优_第1张图片

内容预览:

  • 什么是交叉验证(cross validation)
  • 超参数搜索-网格搜索(Grid Search)
  • 鸢尾花案例增加k值调优
  • 案例:预测FaceBook签到位置
  • 总结

什么是交叉验证(cross validation)

交叉验证的定义

将拿到的训练数据,分为训练和验证集,以下图为例:将数据分成4份,其中一份作为验证集,然后经过4次(组)的测试,每次都更换不同的验证集,即得到4组模型的结果,取平均值作为最终结果。由于是将数据分为4份,所以我们称之为4折交叉验证。

2-04-模型选择与调优_第2张图片

分析

2-04-模型选择与调优_第3张图片

充分利用已有的数据,对当前的数据进行训练、验证,目的就是为了使预测结果更加可靠,成功率更高。

为什么需要交叉验证?

交叉验证目的:为了让被评估的模型更加准确可信

思考

这个只是对于参数得出更好的结果,那么我们应该如何选择或者调优参数呢?

超参数搜索-网格搜索(Grid Search)

如何选择合适的k值?

我们可以采用穷举法,即事先准备一些k值,比如说

k=[1,2,3,4,5,6]

然后将这几个k值一个一个代入到我们的代码中,检测一下哪个k值才是最合适的

类似于暴力破解一样,遍历,一个一个试

什么是超参数搜索-网格搜索(Grid Search)?

2-04-模型选择与调优_第4张图片

模型选择与调优API

2-04-模型选择与调优_第5张图片
2-04-模型选择与调优_第6张图片

鸢尾花案例增加k值调优

# -*- coding: utf-8 -*-

"""
@Time    : 2021/3/16 18:34
@Author  : yuhui
@Email   : [email protected]
@FileName: 2_04_模型选择与调优.py
@Software: PyCharm
"""
from sklearn.datasets import load_iris  # 获取鸢尾花数据
from sklearn.model_selection import train_test_split  # 划分数据集
from sklearn.preprocessing import StandardScaler  # 标准化
from sklearn.neighbors import KNeighborsClassifier  # KNN算法预估器
from sklearn.model_selection import GridSearchCV  # 网格搜索和交叉验证

def knn_iris_GridSearchCV():
	"""用KNN算法对鸢尾花进行分类,添加网格搜索和交叉验证"""
	# 获取数据
	iris = load_iris()

	# 划分数据集
	x_train, x_test, y_train, y_test = train_test_split(iris.data, iris.target, random_state=22)
	# 特征工程:标准化
	transfer = StandardScaler()
	x_train = transfer.fit_transform(x_train)  # 对训练集进行标准化
	# 训练集做了标准化,测试集也需要做标准化
	# 训练集做了什么工作,测试集也应该做同样的工作
	x_test = transfer.transform(x_test)  # 注意:是transform而不是fit_transform
	# 也就是说:使用的是训练集的平均值和标准差
	# 目的是为了和训练集保持一致

	# KNN算法评估器
	estimator = KNeighborsClassifier()
	estimator.fit(x_train, y_train)
	# 已经建立好了模型

	# 添加网格搜索和交叉验证
	# 参数准备
	param_dict={"n_neighbors": [1, 3, 5, 7, 9, 11]}
	estimator = GridSearchCV(estimator, param_grid=param_dict, cv=10)
	estimator.fit(x_train, y_train)

	# 模型评估
	# 方法1:直接比对真实值和预测值
	y_predict = estimator.predict(x_test)
	print("y_predict:\n", y_predict)
	print("直接比对真实值和预测值:\n", y_test == y_predict)

	# 方法2:计算准确率
	score = estimator.score(x_test, y_test)
	print("准确率为:\n", score)

	# 最佳参数:best_params_
	print("最佳参数:\n", estimator.best_params_)
	# 最佳结果:best_score_
	print("最佳结果:\n", estimator.best_score_)
	# 最佳估计器:best_estimator_
	print("最佳估计器:\n", estimator.best_estimator_)
	# 交叉验证结果:cv_results_
	print("交叉验证结果:\n", estimator.cv_results_)

if __name__ == '__main__':
    knn_iris_GridSearchCV()
D:\Anaconda3\Installation\envs\math\python.exe D:/Machine_Learning/Machine_Learning_1/code/2_04_模型选择与调优.py
y_predict:
 [0 2 1 2 1 1 1 2 1 0 2 1 2 2 0 2 1 1 1 1 0 2 0 1 2 0 2 2 2 2 0 0 1 1 1 0 0
 0]
直接比对真实值和预测值:
 [ True  True  True  True  True  True  True  True  True  True  True  True
  True  True  True  True  True  True False  True  True  True  True  True
  True  True  True  True  True  True  True  True  True  True  True  True
  True  True]
准确率为:
 0.9736842105263158
最佳参数:
 {'n_neighbors': 3}
最佳结果:
 0.9553030303030303
最佳估计器:
 KNeighborsClassifier(n_neighbors=3)
交叉验证结果:
 {'mean_fit_time': array([0.00049872, 0.00069816, 0.00069818, 0.00059848, 0.0004988 ,
       0.00055275]), 'std_fit_time': array([0.00049872, 0.00045705, 0.00045707, 0.00048866, 0.0004988 ,
       0.00047017]), 'mean_score_time': array([0.00149605, 0.00149603, 0.00109696, 0.00129654, 0.00149589,
       0.00149271]), 'std_score_time': array([0.0009196 , 0.00049877, 0.00029922, 0.00045741, 0.00066914,
       0.00050213]), 'param_n_neighbors': masked_array(data=[1, 3, 5, 7, 9, 11],
             mask=[False, False, False, False, False, False],
       fill_value='?',
            dtype=object), 'params': [{'n_neighbors': 1}, {'n_neighbors': 3}, {'n_neighbors': 5}, {'n_neighbors': 7}, {'n_neighbors': 9}, {'n_neighbors': 11}], 'split0_test_score': array([0.91666667, 0.91666667, 1.        , 1.        , 0.91666667,
       0.91666667]), 'split1_test_score': array([1., 1., 1., 1., 1., 1.]), 'split2_test_score': array([0.90909091, 0.90909091, 0.90909091, 0.90909091, 0.90909091,
       0.90909091]), 'split3_test_score': array([0.90909091, 1.        , 0.90909091, 0.90909091, 0.90909091,
       1.        ]), 'split4_test_score': array([1., 1., 1., 1., 1., 1.]), 'split5_test_score': array([0.90909091, 0.90909091, 0.90909091, 0.90909091, 0.90909091,
       0.90909091]), 'split6_test_score': array([0.90909091, 0.90909091, 0.90909091, 1.        , 1.        ,
       1.        ]), 'split7_test_score': array([0.90909091, 0.90909091, 0.81818182, 0.81818182, 0.81818182,
       0.81818182]), 'split8_test_score': array([1., 1., 1., 1., 1., 1.]), 'split9_test_score': array([1., 1., 1., 1., 1., 1.]), 'mean_test_score': array([0.94621212, 0.95530303, 0.94545455, 0.95454545, 0.94621212,
       0.95530303]), 'std_test_score': array([0.04397204, 0.0447483 , 0.06030227, 0.06098367, 0.05988683,
       0.0604591 ]), 'rank_test_score': array([4, 1, 6, 3, 4, 1])}

Process finished with exit code 0

2-04-模型选择与调优_第7张图片

补充

在KNN算法中,我们常用的距离有:

  • 曼哈顿距离
  • 欧式距离
  • 明可夫斯基距离

那么我们在代码中,是如何体现我们使用的是哪种距离的呢?

2-04-模型选择与调优_第8张图片

打开之后就是下面的这个样子的

2-04-模型选择与调优_第9张图片

你可能感兴趣的:(算法,python,机器学习,深度学习,人工智能)