分类树
from sklearn import tree
import pandas as pd
import numpy as np
# import graphviz
from sklearn.datasets import load_wine
from sklearn.model_selection import train_test_split
wine = load_wine()
sklearn自带的数据用字典存储
wine.target_names
array(['class_0', 'class_1', 'class_2'], dtype='<U7')
wine.feature_names
['alcohol',
'malic_acid',
'ash',
'alcalinity_of_ash',
'magnesium',
'total_phenols',
'flavanoids',
'nonflavanoid_phenols',
'proanthocyanins',
'color_intensity',
'hue',
'od280/od315_of_diluted_wines',
'proline']
wine.target
array([0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1,
1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 2, 2,
2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2,
2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2,
2, 2])
wine.data
array([[1.423e+01, 1.710e+00, 2.430e+00, ..., 1.040e+00, 3.920e+00,
1.065e+03],
[1.320e+01, 1.780e+00, 2.140e+00, ..., 1.050e+00, 3.400e+00,
1.050e+03],
[1.316e+01, 2.360e+00, 2.670e+00, ..., 1.030e+00, 3.170e+00,
1.185e+03],
...,
[1.327e+01, 4.280e+00, 2.260e+00, ..., 5.900e-01, 1.560e+00,
8.350e+02],
[1.317e+01, 2.590e+00, 2.370e+00, ..., 6.000e-01, 1.620e+00,
8.400e+02],
[1.413e+01, 4.100e+00, 2.740e+00, ..., 6.100e-01, 1.600e+00,
5.600e+02]])
import pandas as pd
pd.concat([pd.DataFrame(wine.data),pd.DataFrame(wine.target)],axis=1)
0 | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 0 | |
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
0 | 14.23 | 1.71 | 2.43 | 15.6 | 127.0 | 2.80 | 3.06 | 0.28 | 2.29 | 5.64 | 1.04 | 3.92 | 1065.0 | 0 |
1 | 13.20 | 1.78 | 2.14 | 11.2 | 100.0 | 2.65 | 2.76 | 0.26 | 1.28 | 4.38 | 1.05 | 3.40 | 1050.0 | 0 |
2 | 13.16 | 2.36 | 2.67 | 18.6 | 101.0 | 2.80 | 3.24 | 0.30 | 2.81 | 5.68 | 1.03 | 3.17 | 1185.0 | 0 |
3 | 14.37 | 1.95 | 2.50 | 16.8 | 113.0 | 3.85 | 3.49 | 0.24 | 2.18 | 7.80 | 0.86 | 3.45 | 1480.0 | 0 |
4 | 13.24 | 2.59 | 2.87 | 21.0 | 118.0 | 2.80 | 2.69 | 0.39 | 1.82 | 4.32 | 1.04 | 2.93 | 735.0 | 0 |
... | ... | ... | ... | ... | ... | ... | ... | ... | ... | ... | ... | ... | ... | ... |
173 | 13.71 | 5.65 | 2.45 | 20.5 | 95.0 | 1.68 | 0.61 | 0.52 | 1.06 | 7.70 | 0.64 | 1.74 | 740.0 | 2 |
174 | 13.40 | 3.91 | 2.48 | 23.0 | 102.0 | 1.80 | 0.75 | 0.43 | 1.41 | 7.30 | 0.70 | 1.56 | 750.0 | 2 |
175 | 13.27 | 4.28 | 2.26 | 20.0 | 120.0 | 1.59 | 0.69 | 0.43 | 1.35 | 10.20 | 0.59 | 1.56 | 835.0 | 2 |
176 | 13.17 | 2.59 | 2.37 | 20.0 | 120.0 | 1.65 | 0.68 | 0.53 | 1.46 | 9.30 | 0.60 | 1.62 | 840.0 | 2 |
177 | 14.13 | 4.10 | 2.74 | 24.5 | 96.0 | 2.05 | 0.76 | 0.56 | 1.35 | 9.20 | 0.61 | 1.60 | 560.0 | 2 |
178 rows × 14 columns
Xtrain, Xtest, Ytrain, Ytest = train_test_split(wine.data,wine.target,test_size=0.3)
参数1:criterion 不纯度计算方式
基尼系数:"gini"和信息熵:“entropy”
两种方式的选择:
1. 通常使用基尼系数,维度低,数据比较清晰的时候,信息熵和基尼系数没区别
2. 信息熵对不纯度更加敏感,对不纯度的惩罚最强,所以信息熵作为指标时,决策树的生长会更加“精细”。
因此对于高维数据或者噪音很多的数据,信息熵很容易 过拟合,基尼系数在这种情况下效果往往比较好。
3. 信息熵的计算比基尼系数缓慢一些,因为基尼系数的计算不涉及对数
4. 模型拟合程度不足的时候,尝试使用信息熵。
clf = tree.DecisionTreeClassifier(criterion="entropy")
clf = clf.fit(Xtrain, Ytrain)
score = clf.score(Xtest, Ytest) #返回预测的准确度accuracy
score
0.8518518518518519
# feature_name = ['酒精','苹果酸','灰','灰的碱性','镁','总酚','类黄酮','非黄烷类酚类','花青素','颜色强度','色调','od280/od315稀释葡萄酒','脯氨酸']
# import graphviz
# dot_data = tree.export_graphviz(clf #经过fit的模型
# ,out_file="Tree.dot" #文件
# ,feature_names = feature_name #特征
# ,class_names=["琴酒","雪莉","贝尔摩德"] #节点类型
# ,filled=True #是否用颜色来标志节点类型,和不纯度
# ,rounded=True #框的形状
# )
# graph=graphviz.Source(dot_data)
# graph
属性:feature_importances_ 特征重要性评分
clf.feature_importances_
array([0.36805967, 0. , 0.01681674, 0.06558588, 0. ,
0. , 0.42692793, 0. , 0. , 0.12260977,
0. , 0. , 0. ])
feature_name = ['酒精','苹果酸','灰','灰的碱性','镁','总酚','类黄酮','非黄烷类酚类','花青素','颜色强度','色调','od280/od315稀释葡萄酒','脯氨酸']
[*zip(feature_name,clf.feature_importances_)]
[('酒精', 0.36805967453506444),
('苹果酸', 0.0),
('灰', 0.016816735253373225),
('灰的碱性', 0.06558588331982633),
('镁', 0.0),
('总酚', 0.0),
('类黄酮', 0.4269279334333496),
('非黄烷类酚类', 0.0),
('花青素', 0.0),
('颜色强度', 0.1226097734583865),
('色调', 0.0),
('od280/od315稀释葡萄酒', 0.0),
('脯氨酸', 0.0)]
参数2:random_state 随机模式
由于不纯度是基于节点进行计算的,决策树在建树时,是靠优化节点来追求一颗优化树,但最优 的节点
并不能够保证最优的树。因此sklearn中的决策树使用了集成算法的思想,建很多的树,然后从中取最好树。
怎样从一组数据集中建不同的树?在每次分枝时,不从使用全部特征,而是随机选取一部分特征,从中选取
不纯度相关指标最优的作为分枝用的节点。这样,每次生成的树也就不同了。
每次选择特征的随机性由random_state参数控制。
random_state默认None,在高维度时随机性会表现更明显,低维度的数据(比如鸢尾花数据集),
随机性几乎不会显现。
clf1= tree.DecisionTreeClassifier(criterion="entropy",random_state=30)
clf1= clf1.fit(Xtrain, Ytrain)
score1 = clf1.score(Xtest, Ytest) #返回预测的准确度
score1
0.8518518518518519
参数3: splitter 控制随机性
有两种输入值,输入”best",决策树在分枝时虽然随机,但是还是会优先选择更重要的特征进行分枝
(重要性可以通过属性feature_importances_查看)。
输入“random",决策树在分枝时会更加随机,树会因为含有更多的不必要信息而更深更大,并因这些
不必要信息而降低对训练集的拟合。这也是防止过拟合的一种方式
clf2= tree.DecisionTreeClassifier(criterion="entropy"
,random_state=30
,splitter="best"
)
clf2 = clf2.fit(Xtrain, Ytrain)
score2 = clf2.score(Xtest, Ytest)
score2
0.8518518518518519
# import graphviz
# dot_data = tree.export_graphviz(clf
# ,feature_names= feature_name
# ,class_names=["琴酒","雪莉","贝尔摩德"]
# ,filled=True
# ,rounded=True
# )
# graph = graphviz.Source(dot_data)
# graph
主要剪枝参数
在不加限制的情况下,一棵决策树会生长到衡量不纯度的指标最优,或者没有更多的特征可用为止。
这样的决策树往往会过拟合
参数:
max_depth:限制树的最大深度,超过设定深度的树枝全部剪掉,在高维度低样本量时非常有效,建议从3开始尝试
参数:
min_samples_leaf:一个节点在分枝后的每个子节点都必须包含至少min_samples_leaf个训练样本,否则分
枝就不会发生,或者,分枝会朝着满足每个子节点都包含min_samples_leaf个样本的方向去发生。
-太小会引起过拟合,设置得太大就会阻止模型学习数据。建议从=5开始使用。
-如果 叶节点中含有的样本量变化很大,建议输入浮点数作为样本量的百分比来使用。
-这个参数可以保证每个叶子的最小尺寸,可以在回归问题中避免低方差,过拟合的叶子节点出现。
-对于类别不多的分类问题,1通常就是最佳选择
参数:
max_samples_split:一个节点必须要包含至少min_samples_split个训练样本,这个节点才允许被分枝,否则
分枝就不会发生
参数:
max_features:限制分枝时考虑的特征个数,超过限制个数的特征都会被舍弃。但改方法比较暴力,是
直接限制可以使用的特征数量而强行使决策树停下的参数,在不知道决策树中的各个特征的重要性的情
况下,强行设定这个参数可能会导致模型学习不足
参数:
min_impurity_decrease:限制信息增益的大小,信息增益小于设定数值的分枝不会发生
#我们的树对训练集的拟合程度如何?
score_train = clf.score(Xtrain, Ytrain)
score_train
1.0
clf3= tree.DecisionTreeClassifier(criterion="entropy"
,random_state=30
,splitter="best"
,max_depth=3
# ,min_samples_leaf=10
# ,min_samples_split=25
)
clf3= clf3.fit(Xtrain, Ytrain)
score3= clf3.score(Xtest, Ytest)
score3
0.8518518518518519
# dot_data = tree.export_graphviz(clf
# ,feature_names= feature_name
# ,class_names=["琴酒","雪莉","贝尔摩德"]
# ,filled=True
# ,rounded=True
# )
# graph = graphviz.Source(dot_data)
# graph
import matplotlib.pyplot as plt
test = []
train=[]
for i in range(10):
clf = tree.DecisionTreeClassifier(max_depth=i+1
,criterion="entropy"
,random_state=30
,splitter="random"
)
clf = clf.fit(Xtrain, Ytrain)
test_score = clf.score(Xtest, Ytest)
test.append(test_score)
train_score = clf.score(Xtrain, Ytrain)
train.append(train_score)
plt.plot(range(1,11),test,color="red",label="test_score")
plt.plot(range(1,11),train,color="blue",label="train_score")
plt.legend()
plt.show()
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-0EfxgHou-1587534022405)(output_36_0.png)]
目标权重参数
参数:
class_weight:完成样本标签平衡的参数。默认为None,此模式表示自动给所有标签相同的权重。
有了权重之后,样本量就不再是单纯地记录数目,而是受输入的权重影响了,因此这时候剪枝,
就需要搭配min_weight_fraction_leaf这个基于权重的剪枝参数来使用
参数:
min_weight_fraction_leaf:改参数比不知道样本权重(比如min_samples_leaf)更少偏向主导类。
如果样本是加权的,则使用基于权重的预修剪标准来更容易优化树结构,这确保叶节点至少包含样
本权重的总和的一小部分
接口:
apply():返回每个测试样本所在的叶子节点的索引
clf.apply(Xtest)
array([ 4, 13, 30, 30, 4, 30, 21, 30, 15, 13, 15, 30, 4, 9, 30, 4, 4,
15, 30, 21, 4, 30, 15, 20, 13, 13, 30, 4, 20, 15, 21, 10, 4, 21,
4, 15, 13, 20, 4, 29, 13, 29, 21, 20, 20, 20, 29, 4, 10, 4, 10,
9, 4, 9], dtype=int64)
predict():返回每个测试样本的分类/回归结果
clf.predict(Xtest)
array([2, 1, 0, 0, 2, 0, 0, 0, 1, 1, 1, 0, 2, 1, 0, 2, 2, 1, 0, 0, 2, 0,
1, 1, 1, 1, 0, 2, 1, 1, 0, 2, 2, 0, 2, 1, 1, 1, 2, 0, 1, 0, 0, 1,
1, 1, 0, 2, 2, 2, 2, 1, 2, 1])
注意:所有接口中要求输入X_train和X_test的部分,输入的特征矩阵必须至少是一个二维矩阵。
sklearn不接受任何一维矩阵作为特征矩阵被输入。如果你的数据的确只有一个特征,那必须用reshape(-1,1)来给
矩阵增维;如果你的数据只有一个特征和一个样本,使用reshape(1,-1)来给你的数据增维。
回归树
from sklearn.datasets import load_boston
from sklearn.model_selection import cross_val_score
from sklearn.tree import DecisionTreeRegressor
boston = load_boston()
boston.data
array([[6.3200e-03, 1.8000e+01, 2.3100e+00, ..., 1.5300e+01, 3.9690e+02,
4.9800e+00],
[2.7310e-02, 0.0000e+00, 7.0700e+00, ..., 1.7800e+01, 3.9690e+02,
9.1400e+00],
[2.7290e-02, 0.0000e+00, 7.0700e+00, ..., 1.7800e+01, 3.9283e+02,
4.0300e+00],
...,
[6.0760e-02, 0.0000e+00, 1.1930e+01, ..., 2.1000e+01, 3.9690e+02,
5.6400e+00],
[1.0959e-01, 0.0000e+00, 1.1930e+01, ..., 2.1000e+01, 3.9345e+02,
6.4800e+00],
[4.7410e-02, 0.0000e+00, 1.1930e+01, ..., 2.1000e+01, 3.9690e+02,
7.8800e+00]])
boston.target
array([24. , 21.6, 34.7, 33.4, 36.2, 28.7, 22.9, 27.1, 16.5, 18.9, 15. ,
18.9, 21.7, 20.4, 18.2, 19.9, 23.1, 17.5, 20.2, 18.2, 13.6, 19.6,
15.2, 14.5, 15.6, 13.9, 16.6, 14.8, 18.4, 21. , 12.7, 14.5, 13.2,
13.1, 13.5, 18.9, 20. , 21. , 24.7, 30.8, 34.9, 26.6, 25.3, 24.7,
21.2, 19.3, 20. , 16.6, 14.4, 19.4, 19.7, 20.5, 25. , 23.4, 18.9,
35.4, 24.7, 31.6, 23.3, 19.6, 18.7, 16. , 22.2, 25. , 33. , 23.5,
19.4, 22. , 17.4, 20.9, 24.2, 21.7, 22.8, 23.4, 24.1, 21.4, 20. ,
20.8, 21.2, 20.3, 28. , 23.9, 24.8, 22.9, 23.9, 26.6, 22.5, 22.2,
23.6, 28.7, 22.6, 22. , 22.9, 25. , 20.6, 28.4, 21.4, 38.7, 43.8,
33.2, 27.5, 26.5, 18.6, 19.3, 20.1, 19.5, 19.5, 20.4, 19.8, 19.4,
21.7, 22.8, 18.8, 18.7, 18.5, 18.3, 21.2, 19.2, 20.4, 19.3, 22. ,
20.3, 20.5, 17.3, 18.8, 21.4, 15.7, 16.2, 18. , 14.3, 19.2, 19.6,
23. , 18.4, 15.6, 18.1, 17.4, 17.1, 13.3, 17.8, 14. , 14.4, 13.4,
15.6, 11.8, 13.8, 15.6, 14.6, 17.8, 15.4, 21.5, 19.6, 15.3, 19.4,
17. , 15.6, 13.1, 41.3, 24.3, 23.3, 27. , 50. , 50. , 50. , 22.7,
25. , 50. , 23.8, 23.8, 22.3, 17.4, 19.1, 23.1, 23.6, 22.6, 29.4,
23.2, 24.6, 29.9, 37.2, 39.8, 36.2, 37.9, 32.5, 26.4, 29.6, 50. ,
32. , 29.8, 34.9, 37. , 30.5, 36.4, 31.1, 29.1, 50. , 33.3, 30.3,
34.6, 34.9, 32.9, 24.1, 42.3, 48.5, 50. , 22.6, 24.4, 22.5, 24.4,
20. , 21.7, 19.3, 22.4, 28.1, 23.7, 25. , 23.3, 28.7, 21.5, 23. ,
26.7, 21.7, 27.5, 30.1, 44.8, 50. , 37.6, 31.6, 46.7, 31.5, 24.3,
31.7, 41.7, 48.3, 29. , 24. , 25.1, 31.5, 23.7, 23.3, 22. , 20.1,
22.2, 23.7, 17.6, 18.5, 24.3, 20.5, 24.5, 26.2, 24.4, 24.8, 29.6,
42.8, 21.9, 20.9, 44. , 50. , 36. , 30.1, 33.8, 43.1, 48.8, 31. ,
36.5, 22.8, 30.7, 50. , 43.5, 20.7, 21.1, 25.2, 24.4, 35.2, 32.4,
32. , 33.2, 33.1, 29.1, 35.1, 45.4, 35.4, 46. , 50. , 32.2, 22. ,
20.1, 23.2, 22.3, 24.8, 28.5, 37.3, 27.9, 23.9, 21.7, 28.6, 27.1,
20.3, 22.5, 29. , 24.8, 22. , 26.4, 33.1, 36.1, 28.4, 33.4, 28.2,
22.8, 20.3, 16.1, 22.1, 19.4, 21.6, 23.8, 16.2, 17.8, 19.8, 23.1,
21. , 23.8, 23.1, 20.4, 18.5, 25. , 24.6, 23. , 22.2, 19.3, 22.6,
19.8, 17.1, 19.4, 22.2, 20.7, 21.1, 19.5, 18.5, 20.6, 19. , 18.7,
32.7, 16.5, 23.9, 31.2, 17.5, 17.2, 23.1, 24.5, 26.6, 22.9, 24.1,
18.6, 30.1, 18.2, 20.6, 17.8, 21.7, 22.7, 22.6, 25. , 19.9, 20.8,
16.8, 21.9, 27.5, 21.9, 23.1, 50. , 50. , 50. , 50. , 50. , 13.8,
13.8, 15. , 13.9, 13.3, 13.1, 10.2, 10.4, 10.9, 11.3, 12.3, 8.8,
7.2, 10.5, 7.4, 10.2, 11.5, 15.1, 23.2, 9.7, 13.8, 12.7, 13.1,
12.5, 8.5, 5. , 6.3, 5.6, 7.2, 12.1, 8.3, 8.5, 5. , 11.9,
27.9, 17.2, 27.5, 15. , 17.2, 17.9, 16.3, 7. , 7.2, 7.5, 10.4,
8.8, 8.4, 16.7, 14.2, 20.8, 13.4, 11.7, 8.3, 10.2, 10.9, 11. ,
9.5, 14.5, 14.1, 16.1, 14.3, 11.7, 13.4, 9.6, 8.7, 8.4, 12.8,
10.5, 17.1, 18.4, 15.4, 10.8, 11.8, 14.9, 12.6, 14.1, 13. , 13.4,
15.2, 16.1, 17.8, 14.9, 14.1, 12.7, 13.5, 14.9, 20. , 16.4, 17.7,
19.5, 20.2, 21.4, 19.9, 19. , 19.1, 19.1, 20.1, 19.9, 19.6, 23.2,
29.8, 13.8, 13.3, 16.7, 12. , 14.6, 21.4, 23. , 23.7, 25. , 21.8,
20.6, 21.2, 19.1, 20.6, 15.2, 7. , 8.1, 13.6, 20.1, 21.8, 24.5,
23.1, 19.7, 18.3, 21.2, 17.5, 16.8, 22.4, 20.6, 23.9, 22. , 11.9])
boston.feature_names
array(['CRIM', 'ZN', 'INDUS', 'CHAS', 'NOX', 'RM', 'AGE', 'DIS', 'RAD',
'TAX', 'PTRATIO', 'B', 'LSTAT'], dtype='<U7')
交叉验证
训练集和测试集的划分会干扰模型的结果,使用交叉验证来观察模型的稳定性。用交叉验证n次的结果
求出的均值是对模型效果的一个更好的度量
regressor = DecisionTreeRegressor(random_state=0) #实例化
cross_val_score(regressor, boston.data, boston.target, cv=10).mean()
-0.1253505322812249
回归树 模型的评估指标
regressor = DecisionTreeRegressor(random_state=0)
cross_val_score(regressor #任何实例化后的分类器
, boston.data #不需要划分训练集和测试集的特征矩阵
, boston.target#不需要划分训练集和测试集的标签
, cv=10, #默认为5,通常使用默认即可
scoring = "neg_mean_squared_error" #模型衡量指标,对于回归树默认为R平方,这里使用负的均方误差
)
array([-16.41568627, -10.61843137, -18.30176471, -55.36803922,
-16.01470588, -44.70117647, -12.2148 , -91.3888 ,
-57.764 , -36.8134 ])
实例:决策树拟合一条包含噪声的正弦曲线
import numpy as np
from sklearn.tree import DecisionTreeRegressor
import matplotlib.pyplot as plt
rng = np.random.RandomState(1) #随机数种子
X = np.sort(5 * rng.rand(80,1), axis=0) #生成0~5之间随机的x的取值
#这里生成1个 80×1的二维矩阵。因为要将数据导入分类树拟合,而sklearn不支持一维特征矩阵的输入
y = np.sin(X).ravel() #生成Y,并将标签降为一维
y[::5] += 2 * (0.5 - rng.rand(16)) #在正弦曲线上加噪声
#y[::5] 在一维array上每隔5个数取一个值
plt.figure()
plt.scatter(X, y, s=20, edgecolor="black",c="darkorange", label="data")
<matplotlib.collections.PathCollection at 0x9a6a848>
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-vk2P0CMx-1587534022409)(output_60_1.png)]
regr_1 = DecisionTreeRegressor(max_depth=2)
regr_2 = DecisionTreeRegressor(max_depth=5)
regr_1.fit(X, y)
regr_2.fit(X, y)
DecisionTreeRegressor(ccp_alpha=0.0, criterion='mse', max_depth=5,
max_features=None, max_leaf_nodes=None,
min_impurity_decrease=0.0, min_impurity_split=None,
min_samples_leaf=1, min_samples_split=2,
min_weight_fraction_leaf=0.0, presort='deprecated',
random_state=None, splitter='best')
X_test = np.arange(0.0, 5.0, 0.01)[:, np.newaxis]
y_1 = regr_1.predict(X_test)
y_2 = regr_2.predict(X_test)
plt.figure()
plt.scatter(X, y, s=20, edgecolor="black",c="darkorange", label="data")
plt.plot(X_test, y_1, color="cornflowerblue",label="max_depth=2", linewidth=2)
plt.plot(X_test, y_2, color="yellowgreen", label="max_depth=5", linewidth=2)
plt.xlabel("data")
plt.ylabel("target")
plt.title("Decision Tree Regression")
plt.legend()
plt.show()
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-GkYUwQuN-1587534022414)(output_64_0.
可以看到,树的最大深度设置的太高,决策树就会学习的越精细,它从训练数据中学了很多细节,
包括噪声,使模型偏离真实的正弦曲线,形成过拟合