机器学习实战之工业蒸汽

题目基本情况

数据集

1
2
1.数据集:
https://tianchi.aliyun.com/dataset/dataDetail?dataId=130516

数据探索

理论知识

赛题数据探索

导入工具包

1
2
3
4
5
6
7
8
9
10
11
12

import numpy as np
import pandas as pd
import matplotlib.pyplot as plt
import seaborn as sns
import warnings
from scipy import stats
#1.读取数据
train_data_file = "zhengqi_train.txt"
test_data_file = "zhengqi_test.txt"
train_data = pd.read_csv(train_data_file, sep='\t', encoding='utf-8') #训练集数据共有2888个样本(V0-V37共38个特征变量) -- 有target字段
test_data = pd.read_csv(test_data_file, sep='\t', encoding='utf-8') #测试集数据共有1925个样本(V0-V37共有38个特征变量) -- 无target字段

可视化数据分布

箱型图(boxplot)

1
2
3
4
5
6
##2.1 箱型图boxplot(所有特征变量)
columns=train_data.columns.tolist()[:39] #前39列
fig=plt.figure(figsize=(20,40)) #指定绘图对象宽度和高度
for i in range(38):
plt.subplot(8,5,i+1) #指定8行5列子图
sns.boxplot(train_data[columns[i]],orient="h",width=0.5) #orient是v(垂直)/h(水平)

整体的箱型图:

V0一个的箱型图:

直方图(distplot)和Q-Q图(probplot)

1
2
3
4
5
6
7
8
9
10
11
12
##2.3 直方图distplot和Q-Q图probplot(数据的分位数和正态分布的分位数对比参照) -- 如果数据符合正态分布 会在qq图内两条线重合
train_cols=6 #列
train_rows=len(train_data.columns) #行
plt.figure(figsize=(train_cols,train_rows)) #指定绘图对象宽度和高度
i=0
for col in train_data.columns:
i+=1
ax=plt.subplot(train_rows,train_cols,i) #指定r行c列子图第i个位置
sns.distplot(train_data[col],fit=stats.norm) #fit设置函数图像(与原图进行比较)
i+=1
ax=plt.subplot(train_rows,train_cols,i) # 指定r行c列子图第i+1个位置
res=stats.probplot(train_data[col],plot=plt) # fit设置函数图像(与原图进行比较)

KDE分布图(核密度估计kdeplot)

1
2
3
4
5
6
7
8
9
10
11
12
13
##2.4 KDE分布图kdeplot(核密度估计) --对直方图的加窗平滑(可以查看对比训练集和测试集中特征变量的分布情况)
dist_cols=6 #列
dist_rows=len(test_data.columns) #行
plt.figure(figsize=(train_cols,train_rows)) #指定绘图对象宽度和高度
i=1
for col in test_data.columns:
ax=plt.subplot(dist_rows,dist_cols,i) #指定r行c列子图第i个位置
ax=sns.kdeplot(train_data[col],color="Red",shade=True)
ax=sns.kdeplot(test_data[col], color="Blue", shade=True)
ax.set_xlabel(col) #横坐标名称
ax.set_ylabel("Frequency") #纵坐标名称
ax=ax.legend(["训练集","测试集"]) #两条曲线的名称
i=i+1

线性回归关系图(regplot)

1
2
3
4
5
6
7
8
9
10
11
12
##2.5 线性回归关系图regplot(分析变量之间的线性回归关系)
fcols=6 #列
frows=len(test_data.columns) #行
plt.figure(figsize=(fcols,frows)) #指定绘图对象宽度和高度
i=0
for col in test_data.columns:
i=i+1
ax=plt.subplot(frows,fcols,i) #指定r行c列子图第i个位置
sns.regplot(x=col,y='target',data=train_data,ax=ax,scatter_kws={'marker':'.','s':3,'alpha':0.3},line_kws={'color':'k'})
plt.xlabel(col)
plt.ylabel('target')
plt.show()

查看特征变量的相关性

计算相关性系数(data.corr)

1
2
3
4
5
6
7
#3.查看特征变量的相关性
##3.1 计算相关性系数corr --> KDE图中拿训练集和测试集中分布不一致的特征变量进行删除(V5,V9,V11,V17,V22,V28) --> 计算剩余特征变量和target变量的相关性系数
pd.set_option('display.max_columns',10) #显示10列 默认none就是最多
pd.set_option('display.max_rows',10) #显示10行
data_train1=train_data.drop(['V5','V9','V11','V17','V22','V28'],axis=1) #删除那些测试集和训练集分布不一致的特征向量
train_corr=data_train1.corr() #corr给出任意两个变量之间的相关系数
print(train_corr)

相关热力图(sns.heatmap)

1
2
3
##3.2 热力图heatmap
ax=plt.subplots(figsize=(20,16)) #调整画布大小
ax=sns.heatmap(train_corr,vmax=.8,square=True,annot=True) #vmax和vmin是图例中最大值和最小值的显示值 square为热力图矩阵小块形状(T以列名为标签名) annot为T表示每个方格写入数据

根据相关系数筛选特征变量(相关性选择/树模型)

1
2
3
4
5
6
7
8
###3.3.1 寻找k个与target变量最相关的特征变量(K=10)
columns=train_corr.nlargest(10,'target') #利用相关系数.nlargest()获取
columnsindex=columns['target'].index # 获取符合的下标'V0'/'V1'/'V8'/'V27'/'V31'/'V2'/'V4'/'V12'/'V16'
columnsvalue=train_data[columnsindex].values #找到k个特征变量在训练集中的值
cm=np.corrcoef(columnsvalue) #皮尔逊积矩相关系数--计算两个变量x和y之间的线性相关(-1到1)
ax=plt.subplots(figsize=(10,10)) #调整画布大小
ax=sns.heatmap(train_data[columnsindex].corr(),annot=True,square=True) #k个相关值画热力图
plt.show()

1
2
3
4
5
6
###3.3.2 找出与target变量的相关系数大于0.5的特征变量
corrs=train_data.corr() #获取训练数据集的相关系数
corrres=corrs.index[abs(corrs['target'])>0.5] # 获取符合的下标 V0'/'V1'/'V2'/'V3'/'V4'/'V8'/'V12'/'V16'/'V27'/'V31'/'V37'
ax=plt.figure(figsize=(10,10))
ax=sns.heatmap(train_data[corrres].corr(),annot=True,cmap="RdYlGn") #cmap设置颜色
plt.show()

Box-Cox变换

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
###3.3.3 Box-Cox变换(线性回归基于正态分布 --> 统计分析将数据转换为符合正态分布)
####1. 合并数据
drop_columns = ['V5','V9','V11','V17','V22','V28'] #KDE图发现训练集和测试集中这几个特征变量不一致 需要删除
train_droptarget=train_data.drop(['target'],axis=1) #按照axis=1列删除了target的行和列(因为train里面比test多了target列)
data_all=pd.concat([train_droptarget,test_data]) #默认纵向拼接train和test两个训练集(列不变 行数会变多)
data_all.drop(drop_columns,axis=1,inplace=True) #按照axis=1列删除那些列
####2. 归一化(1.MinMaxScaler函数/2.min-max离差标准化)
colunms_list=list(data_all.columns) #对合并后的每列数据合成一个list列表
def scale_minmax(col): #定义一个标准化的函数用于apply方法的第一个参数
return (col-col.min())/(col.max()-col.min())
data_all[colunms_list]=data_all[colunms_list].apply(scale_minmax,axis=0) # axis=0对每一列数据应用函数

####3. Box-Cox变换
data_all, lambda0 = boxcox1p(data_all)

####4. 重新画Q-Q图
data_all_cols=6 #列
data_all_rows=len(data_all.columns) #行
plt.figure(figsize=(data_all_cols,data_all_rows)) #指定绘图对象宽度和高度
i=0
for col in data_all.columns:
i+=1
ax=plt.subplot(data_all_rows,data_all_cols,i) #指定r行c列子图第i个位置
sns.distplot(data_all[col],fit=stats.norm) #fit设置函数图像(与原图进行比较)
i+=1
ax=plt.subplot(data_all_rows,data_all_cols,i) # 指定r行c列子图第i+1个位置
res=stats.probplot(data_all[col],plot=plt) # fit设置函数图像(与原图进行比较)
plt.show()

特征工程

特征工程的重要性和处理

特征工程的重要性:

1
2
3
4
5
6
 1.特征工程处理流程:
1.1 去掉无用特征
1.2 去掉冗余特征(如共线特征)
1.3 生成新特征(利用存在的特征、转换特征、内容中的特征、其他数据源)
1.4 特征转换(数值化、类别转换、归一化等)
1.5 特征处理(异常值、最大值、最小值、缺失值)

数据预处理和特征处理

数据预处理(数据采集+数据清洗+数据采样)

数据采集

数据清洗

数据采样

1
2
3
4
5
6
7
1.数据采样的原因:经过采集和清洗之后正负样本是不均衡的 --> 数据采样
2.数据采样的方法:
2.1 随机采样: 可能随机采样得到的数据很不均匀
2.2 分层采样:
3.正负样本不均衡的处理办法:
3.1 正样本>负样本 + 量特别大 : 下采样(downsampling)的方法
3.2 正样本>负样本 + 量不大 : 上采样(oversampling)的方法(图像识别的镜像和旋转/修改损失函数设置样本权重)

特征处理

特征处理小结:

标准化(StandardScaler类)

1
2
3
1.标准化: 依照特征矩阵的列去处理数据[通过求标准分数的方法将特征-->标准正态分布]
2.使用场景:
2.1 数据存在异常值和较多噪声

区间缩放法(MinMaxScaler类)

1
1.区间缩放法: 利用两个最值(最大值和最小值)进行缩放 [归一化的一种]

归一化(Normalizer类)

公式:

1
2
3
4
1.归一化: 样本的特征值-->同一量纲,数据-->[0,1]/[a,b]区间内
2.使用场景:
2.1 输出结果范围有要求
2.2 数据较为稳定,不存在极端的最大值/最小值

定量特征二值化(Binarizer类)

公式:

1
1. 定量特征二值化: 核心在于设定一个阈值(>阈值的赋值为1,≤阈值的赋值为0)

定性特征哑编码(OneHotEncoder类)

1
2
3
4
5
6
1.哑变量/虚拟变量(Dummy Variable):通常是认为虚设的变量(0/1),用来反映某个变量的不同属性。
2.哑变量目的: 原本不能定量处理的变量进行量化,从而评估定性因素对因变量的影响
2.1 例如: 变量"职业"取值分别为工人、农民、学生、企业职员、其他(5种选项) --> 工人定义为(0,0,0,1) 那么农民就是(0,0,1,0) 学生就是(0,1,0,0) 企业职工就是(1,0,0,0)

2.哑编码: 类别变量 --> 哑变量
3.哑编码规则:对于有n个类别属性的变量,通常以1个类别特征为参照,产生n-1个哑变量

缺失值处理(impute库的SimpleImputer类)

1
2
1.用Pandas读取后特征均为NaN(数据缺失)
2.使用impute库的SimpleImputer类

数据转换

1
2
3
1.基于多项式的多项式转换(PolynomialFeatures类):参数degree为度(默认值为2)
2.基于对数函数的对数变换:基于单变元函数的数据转换可以使用统一的方法完成(FunctionTransformer类)
3.基于指数函数:

特征降维

特征选择

特征选择三类方法:

1
2
3
4
5
1.特征选择概念:比较简单粗暴,就是映射函数直接将不重要的特征(×),不过会造成特征信息的丢失,不利用模型精度
2.特征选择方法:
2.1 过滤法(Filter):按照发散性/相关性对各个特征进行评分,通过设定阈值/待选择阈值的个数来选择特征
2.2 包装法(Wrapper):按照目标函数(AUC/MSE)每次选择/排除若干特征
2.3 嵌入法(Embedded):使用某些算法和模型进行训练,得到各个特征的权值系数,根据系数从大到小选择特征

线性降维

赛题特征工程

异常值分析(箱线图找出异常删除异常)

1
2
3
4
5
6
7
8
9
10
##箱型图
plt.figure(figsize=(18,10))
plt.boxplot(x=train_data.values,labels=train_data.columns) #标签就是训练集的各个列
plt.hlines([-7.5,7.5],0,40,colors='r') #从-7.5到7.5绘制水平线 0和40就是这条线从第几个Vx开始画到第Vx个特征
plt.show()
##删除异常值(通过箱型图可以查看到明显的异常值【比如V9变量】)
train_data=train_data[train_data['V9']>-7.5]
test_data=test_data[test_data['V9']>-7.5]
print(train_data.describe())
print(test_data.describe())

归一化(最大值和最小值)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
##归一化(最大值和最小值)  --放缩到(0,1区间)
features_columns=[col for col in train_data.columns if col not in ['target']] #从V0到V37
min_max_scaler=preprocessing.MinMaxScaler().fit(train_data[features_columns])

train_data_scaler=min_max_scaler.transform(train_data[features_columns])
test_data_scaler=min_max_scaler.transform(test_data[features_columns])

train_data_scaler=pd.DataFrame(train_data_scaler) #将训练集数据弄成DF格式
train_data_scaler.columns=features_columns

test_data_scaler=pd.DataFrame(test_data_scaler) #将测试集数据弄成DF格式
test_data_scaler.columns=features_columns

train_data_scaler['target'] = train_data['target']

print(train_data_scaler.describe())
print(test_data_scaler.describe())

查看数据分布(KDE差异较大删除特征)

1
2
3
4
5
6
7
8
9
10
11
12
##查看数据分布  --通过KDE分布对比了特征变量在两个数据集中的分布情况(V5/V9/V11/V17/V22/V28在训练集和测试集分布差异较大,会影响模型的泛化能力,故删除这些特征)
drop_col=6 #6列
drop_row=1 #1行
plt.figure(figsize=(5*drop_col,5*drop_row))
for i,col in enumerate(["V5","V9","V11","V17","V22","V28"]): #enumerate函数用于将一个可遍历的数据对象
ax=plt.subplot(1,6,i+1)
ax=sns.kdeplot(train_data_scaler[col],color="Red",shade=True) #画KDE图
ax=sns.kdeplot(test_data_scaler[col],color="Blue",shade=True) #画KDE图
ax.set_xlabel(col) #设置x标签为col
ax.set_ylabel("Frequency") #设置y标签为Frequency
ax=ax.legend(["train", "test"]) #设置两条曲线分别叫train和test
plt.show()

特征相关性(用热力图可视化)

1
2
3
4
5
6
7
8
9
10
##特征相关性(热力图可视化显示)
plt.figure(figsize=(20,16))
column=train_data_scaler.columns.tolist() # 整出来一个列表list表示从V0-V39-target
mcorr=train_data_scaler[column].corr(method="spearman") # spearman表示非线性的 pearson表示相关系数 kendall反映分类变量相关性的指标(无序序列的相关系数)
# zeros_like()函数: 创建一个和mcorr同维度的数组(初始化全为False)
mask=np.zeros_like(mcorr,dtype=np.bool)
# triu_indices_from()函数: 返回矩阵的上三角(上三角全为True)
mask[np.triu_indices_from(mask)]=True
g=sns.heatmap(mcorr,mask=mask,square=True,annot=True,fmt='0.2f') # square为热力图矩阵小块形状(T以列名为标签名) annot为True表示每个方格写入数据 fmt表示小数点后两位
plt.show()

特征降维

1
2
3
4
##特征降维(特征相关性的初筛--计算相关性系数并筛选>0.1的特征变量)
mcorr=mcorr.abs() #将所有取绝对值
numberical_corr=mcorr[mcorr['target']>0.1]['target']
print(numberical_corr.sort_values(ascending=False)) # VX和系数值 (按照系数值进行排序)

多重共线性分析(statsmodels.stats.outliers_influence.variance_inflation_factor)

1
2
3
4
5
6
##多重共线性分析(特征组之间的相关性系数较大) -- 每个特征变量与其他特征变量之间的相关性系数较大所以存在较大的共线性影响 --> 使用PCA进行处理(去除多重共线性)
###statsmodels.stats.outliers_influence.variance_inflation_factor 多重共线性方差膨胀因子
new_numberical=['V0', 'V2', 'V3', 'V4', 'V5', 'V6', 'V10','V11', 'V13', 'V15', 'V16', 'V18', 'V19', 'V20', 'V22','V24','V30', 'V31', 'V37']
X=np.matrix(train_data_scaler[new_numberical]) #根据new_numberical来构成一个二维数组
VIF_list=[variance_inflation_factor(X,i) for i in range(X.shape[1])] # 获得多重共线性方差膨胀因子
print(VIF_list)

PCA处理(去除数据的多重共线性,并进行降维)

1
2
3
4
5
6
7
8
9
10
11
12
13
##PCA处理
### sklearn.decomposition.PCA PCA处理之后可保持90%的信息数据
pca=PCA(n_components=0.9) # 整数表示保留几个特征 小数表示百分之多少的信息
#获得转换器
new_train_pca_90=pca.fit_transform(train_data_scaler.iloc[:,0:-1])
new_test_pca_90=pca.transform(test_data_scaler)
#转移为DF格式
new_train_pca_90=pd.DataFrame(new_train_pca_90)
new_test_pca_90=pd.DataFrame(new_test_pca_90)
new_train_pca_90['target']=train_data_scaler['target'] # PCA处理之后保留了16个主成分
print(new_train_pca_90.describe())
print("----------------------------------------------")
print(train_data_scaler.describe())

模型训练

回归和相关模型

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
import numpy as np
import pandas as pd
import matplotlib.pyplot as plt
import seaborn as sns
from sklearn import preprocessing
from sklearn.preprocessing import MinMaxScaler
from scipy import stats
from sklearn.decomposition import PCA
from sklearn.model_selection import train_test_split
from sklearn.linear_model import LinearRegression #线性回归
from sklearn.neighbors import KNeighborsRegressor #K近邻回归
from sklearn.tree import DecisionTreeRegressor #决策树回归
from sklearn.ensemble import RandomForestRegressor #随机森林回归
from sklearn.svm import SVR # 支持向量回归
from sklearn.model_selection import train_test_split # 切分数据
from sklearn.metrics import mean_squared_error #评价指标
from sklearn.model_selection import learning_curve
from sklearn.model_selection import ShuffleSplit
#1.读取数据
train_data_file = "zhengqi_train.txt"
test_data_file = "zhengqi_test.txt"
train_data = pd.read_csv(train_data_file, sep='\t', encoding='utf-8') #训练集数据共有2888个样本(V0-V37共38个特征变量) -- 有target字段
test_data = pd.read_csv(test_data_file, sep='\t', encoding='utf-8') #测试集数据共有1925个样本(V0-V37共有38个特征变量) -- 无target字段


#3.归一化(最大值和最小值) --放缩到(0,1区间)
features_columns=[col for col in train_data.columns if col not in ['target']] #从V0到V37
min_max_scaler=preprocessing.MinMaxScaler().fit(train_data[features_columns])

train_data_scaler=min_max_scaler.transform(train_data[features_columns])
test_data_scaler=min_max_scaler.transform(test_data[features_columns])

train_data_scaler=pd.DataFrame(train_data_scaler) #将训练集数据弄成DF格式
train_data_scaler.columns=features_columns

test_data_scaler=pd.DataFrame(test_data_scaler) #将测试集数据弄成DF格式
test_data_scaler.columns=features_columns

train_data_scaler['target'] = train_data['target']

#3.PCA处理
### 1.sklearn.decomposition.PCA PCA处理之后可保持90%的信息数据
pca=PCA(n_components=0.9) # 整数表示保留几个特征 小数表示百分之多少的信息
#获得转换器
new_train_pca_90=pca.fit_transform(train_data_scaler.iloc[:,0:-1])
new_test_pca_90=pca.transform(test_data_scaler)
#转移为DF格式
new_train_pca_90=pd.DataFrame(new_train_pca_90)
new_test_pca_90=pd.DataFrame(new_test_pca_90)
new_train_pca_90['target']=train_data_scaler['target'] # PCA处理之后保留了16个主成分
### 2.sklearn.decomposition.PCA PCA处理之后可保持95%的信息数据
pca = PCA(n_components=0.95)
#获得转换器
new_train_pca_16 = pca.fit_transform(train_data_scaler.iloc[:,0:-1])
new_test_pca_16 = pca.transform(test_data_scaler)
#转移为DF格式
new_train_pca_16 = pd.DataFrame(new_train_pca_16)
new_test_pca_16 = pd.DataFrame(new_test_pca_16)
new_train_pca_16['target'] = train_data_scaler['target'] # PCA处理之后保留了16个主成分

#2.切分数据(训练集--> 80%训练集和20%验证数据)
new_train_pca_16=new_train_pca_16.fillna(0) #采用PCA保留16维特征的数据
train=new_train_pca_16[new_test_pca_16.columns]
target=new_train_pca_16['target']
##切分数据 训练数据80% 验证数据20%
train_data,test_data,train_target,test_target=train_test_split(train,target,test_size=0.2,random_state=0)

#4.线性回归
clf=LinearRegression() #实例化
clf.fit(train_data,train_target) #创建训练集的转换器
test_pred=clf.predict(test_data) #获得测试集的预测
score=mean_squared_error(test_target,test_pred) #判断测试集的目标值和测试集的预测值
print("线性回归预测结果:",score) # 结果为0.13468236081062834

#5.K近邻
clf=KNeighborsRegressor(n_neighbors=3) # k取3
clf.fit(train_data,train_target)
test_pred=clf.predict(test_data)
score=mean_squared_error(test_target,test_pred)
print("K近邻回归预测结果:",score) # 结果为0.22391053287197232

#6.决策树回归
clf=DecisionTreeRegressor()
clf.fit(train_data,train_target)
test_pred=clf.predict(test_data)
score=mean_squared_error(test_target,test_pred)
print("决策树回归预测结果:",score) # 结果为0.33070805190311414

#7.随机森林回归
clf=RandomForestRegressor(n_estimators=200) #创建200课树的模型
clf.fit(train_data,train_target)
test_pred=clf.predict(test_data)
score=mean_squared_error(test_target,test_pred)
print("随机森林回归预测结果:",score) # 结果为

#8.LightGBM回归(微软开发的一个GBDT算法框架--更快的训练速度,更低的内存消耗,更好的准确率,处理海量数据)
##(1)连续的浮点特征值 --> k个整数 + (2)构造一个宽度为k的直方图 [遍历时,将离散化后的值作为索引在直方图中积累统计量]

赛题模型训练

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
import numpy as np
import pandas as pd
import matplotlib.pyplot as plt
import seaborn as sns
from sklearn import preprocessing
from sklearn.preprocessing import MinMaxScaler
from scipy import stats
from sklearn.decomposition import PCA
from sklearn.model_selection import train_test_split
from sklearn.linear_model import LinearRegression #线性回归
from sklearn.neighbors import KNeighborsRegressor #K近邻回归
from sklearn.tree import DecisionTreeRegressor #决策树回归
from sklearn.ensemble import RandomForestRegressor #随机森林回归
from sklearn.svm import SVR # 支持向量回归
import lightgbm as lgb # LightGBM模型
from sklearn.model_selection import train_test_split # 切分数据
from sklearn.metrics import mean_squared_error #评价指标
from sklearn.model_selection import learning_curve
from sklearn.model_selection import ShuffleSplit
#1.读取数据
train_data_file = "zhengqi_train.txt"
test_data_file = "zhengqi_test.txt"
train_data = pd.read_csv(train_data_file, sep='\t', encoding='utf-8') #训练集数据共有2888个样本(V0-V37共38个特征变量) -- 有target字段
test_data = pd.read_csv(test_data_file, sep='\t', encoding='utf-8') #测试集数据共有1925个样本(V0-V37共有38个特征变量) -- 无target字段

#3归一化(最大值和最小值) --放缩到(0,1区间)
features_columns=[col for col in train_data.columns if col not in ['target']] #从V0到V37
min_max_scaler=preprocessing.MinMaxScaler().fit(train_data[features_columns])

train_data_scaler=min_max_scaler.transform(train_data[features_columns])
test_data_scaler=min_max_scaler.transform(test_data[features_columns])

train_data_scaler=pd.DataFrame(train_data_scaler) #将训练集数据弄成DF格式
train_data_scaler.columns=features_columns

test_data_scaler=pd.DataFrame(test_data_scaler) #将测试集数据弄成DF格式
test_data_scaler.columns=features_columns

train_data_scaler['target'] = train_data['target']

#3.PCA处理
### 1.sklearn.decomposition.PCA PCA处理之后可保持90%的信息数据
pca=PCA(n_components=0.9) # 整数表示保留几个特征 小数表示百分之多少的信息
#获得转换器
new_train_pca_90=pca.fit_transform(train_data_scaler.iloc[:,0:-1])
new_test_pca_90=pca.transform(test_data_scaler)
#转移为DF格式
new_train_pca_90=pd.DataFrame(new_train_pca_90)
new_test_pca_90=pd.DataFrame(new_test_pca_90)
new_train_pca_90['target']=train_data_scaler['target'] # PCA处理之后保留了16个主成分
### 2.sklearn.decomposition.PCA PCA处理之后可保持95%的信息数据
pca = PCA(n_components=0.95)
#获得转换器
new_train_pca_16 = pca.fit_transform(train_data_scaler.iloc[:,0:-1])
new_test_pca_16 = pca.transform(test_data_scaler)
#转移为DF格式
new_train_pca_16 = pd.DataFrame(new_train_pca_16)
new_test_pca_16 = pd.DataFrame(new_test_pca_16)
new_train_pca_16['target'] = train_data_scaler['target'] # PCA处理之后保留了16个主成分

#2.切分数据(训练集--> 80%训练集和20%验证数据)
new_train_pca_16=new_train_pca_16.fillna(0) #采用PCA保留16维特征的数据
train=new_train_pca_16[new_test_pca_16.columns]
target=new_train_pca_16['target']
##切分数据 训练数据80% 验证数据20%
train_data,test_data,train_target,test_target=train_test_split(train,target,test_size=0.2,random_state=0)

#4.线性回归(效果一般,适合分析使用)
clf=LinearRegression() #实例化
clf.fit(train_data,train_target) #创建训练集的转换器
test_pred=clf.predict(test_data) #获得测试集的预测
score=mean_squared_error(test_target,test_pred) #判断测试集的目标值和测试集的预测值
print("线性回归预测结果:",score) # 结果为0.13468236081062834

#5.K近邻(效果一般)
clf=KNeighborsRegressor(n_neighbors=8) # k取8 最近8个
clf.fit(train_data,train_target)
test_pred=clf.predict(test_data)
score=mean_squared_error(test_target,test_pred)
print("K近邻回归预测结果:",score) # 结果为0.22391053287197232

#6.决策树回归
clf=DecisionTreeRegressor()
clf.fit(train_data,train_target)
test_pred=clf.predict(test_data)
score=mean_squared_error(test_target,test_pred)
print("决策树回归预测结果:",score) # 结果为0.33070805190311414

#7.随机森林回归(比较合适)
clf=RandomForestRegressor(n_estimators=200) #创建200课树的模型
clf.fit(train_data,train_target)
test_pred=clf.predict(test_data)
score=mean_squared_error(test_target,test_pred)
print("随机森林回归预测结果:",score) # 结果为

#8.LightGBM回归(微软开发的一个GBDT算法框架--更快的训练速度,更低的内存消耗,更好的准确率,处理海量数据)
##(1)连续的浮点特征值 --> k个整数 + (2)构造一个宽度为k的直方图 [遍历时,将离散化后的值作为索引在直方图中积累统计量]
clf=lgb.LGBMRegressor(
learning_rate=0.01, # 学习率 推荐的候选值为:[0.01, 0.015, 0.025, 0.05, 0.1]
max_depth=-1, # 指定树的最大深度(防止过拟合)
n_estimators=5000, # 树的数量
boosting_type='gbdt', # 指定弱学习器的类型 -- gbdt表示使用基于树的模型进行计算(默认)/gblinear表示使用线性模型/rf使用随机森林
random_state=2019,
objective='regression' # regression是使用L2正则项的回归模型(默认) /regression_l1是使用L1正则项的回归模型 /mape平均绝对百分比误差 /binary二分类 /multiclass多分类
)
##训练模型
clf.fit(X=train_data,y=train_target,eval_metric='MSE') #eval_metric表示评价指标(默认是logloss) MSE是均方误差
test_pred=clf.predict(test_data)
score=mean_squared_error(test_target,test_pred)
print("lightGbm回归预测结果:",score)

模型验证

模型评估的概念和方法

欠拟合和过拟合

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
import numpy as np
import pandas as pd
import matplotlib.pyplot as plt
import seaborn as sns
from sklearn import preprocessing
from sklearn.preprocessing import MinMaxScaler
from scipy import stats
from sklearn.decomposition import PCA
from sklearn.model_selection import train_test_split
from sklearn.linear_model import LinearRegression #线性回归
from sklearn.neighbors import KNeighborsRegressor #K近邻回归
from sklearn.tree import DecisionTreeRegressor #决策树回归
from sklearn.ensemble import RandomForestRegressor #随机森林回归
from sklearn.svm import SVR # 支持向量回归
import lightgbm as lgb # LightGBM模型
from sklearn.model_selection import train_test_split # 切分数据
from sklearn.metrics import mean_squared_error #评价指标
from sklearn.model_selection import learning_curve
from sklearn.model_selection import ShuffleSplit
from sklearn.pipeline import Pipeline
from sklearn.preprocessing import PolynomialFeatures
from sklearn.preprocessing import StandardScaler
#1.读取数据
train_data_file = "zhengqi_train.txt"
test_data_file = "zhengqi_test.txt"
train_data = pd.read_csv(train_data_file, sep='\t', encoding='utf-8') #训练集数据共有2888个样本(V0-V37共38个特征变量) -- 有target字段
test_data = pd.read_csv(test_data_file, sep='\t', encoding='utf-8') #测试集数据共有1925个样本(V0-V37共有38个特征变量) -- 无target字段

#生成数据集并可视化显示
np.random.seed(666) #随机生成666个种子
x=np.random.uniform(-3.0,3.0,size=100) #随机数的最小值是-3.0 最大值是3.0
X=x.reshape(-1,1) #reshape更改数据的行列数目
y=0.5*x**2+x+2+np.random.normal(0,1,size=100)
plt.scatter(x,y) #生成散点图
plt.show()

#1.使用线性回归模型对数据进行拟合
lin_reg=LinearRegression()
lin_reg.fit(X,y)
print("准确率为:",lin_reg.score(X,y)) #准确率约为0.495(比较低) --可见直线拟合数据的程度较低
##使用均方误差来评价拟合程度
y_predict=lin_reg.predict(X)
print("均方误差为:",mean_squared_error(y,y_predict)) # 均方误差为3.0750025765636577
##绘制拟合结果
plt.scatter(x,y)
plt.plot(np.sort(x),y_predict[np.argsort(x)],color='r')
plt.show()

#2.使用多项式回归拟合(2.1封装Pipeline管道 2.2使用Pipeline拟合数据,多项式参数设置为degree=x)
##2.1 封装Pipeline管道(以便于下一步灵活调整多项式回归模型参数)
def PolynomialRegression(degree):
return Pipeline(
[('poly',PolynomialFeatures(degree=degree)),
('std_scaler',StandardScaler()),
('lin_reg',LinearRegression())])

##2.2使用Pipeline拟合数据(多项式参数设置为degree=2)
poly2_reg=PolynomialRegression(degree=2) #使用degree=2
poly2_reg.fit(X,y)
y2_predict=poly2_reg.predict(X)
print("degree为2时候的均方误差为:",mean_squared_error(y,y2_predict)) # 均方误差为1.0987392142417858
##绘制拟合结果
plt.scatter(x,y)
plt.plot(np.sort(x),y2_predict[np.argsort(x)],color='r')
plt.show()

##2.2使用Pipeline拟合数据(多项式参数设置为degree=10)
poly10_reg=PolynomialRegression(degree=10) #使用degree=10
poly10_reg.fit(X,y)
y10_predict=poly10_reg.predict(X)
print("degree为10时候的均方误差为:",mean_squared_error(y,y10_predict)) # 均方误差为1.050846676376416
##绘制拟合结果
plt.scatter(x,y)
plt.plot(np.sort(x),y10_predict[np.argsort(x)],color='r')
plt.show()

##2.3使用Pipeline拟合数据(多项式参数设置为degree=100)
poly100_reg=PolynomialRegression(degree=100) #使用degree=100
poly100_reg.fit(X,y)
y100_predict=poly100_reg.predict(X)
print("degree为100时候的均方误差为:",mean_squared_error(y,y100_predict)) # 均方误差为0.6831833931625624
##绘制拟合结果
plt.scatter(x,y)
plt.plot(np.sort(x),y100_predict[np.argsort(x)],color='r')
plt.show()

模型的泛化与正则化

回归模型的评估指标和调用方法

四种回归模型评估方法:

四种回归模型评估的公式:

交叉验证

1.简单交叉验证

2.K折交叉验证

3.留一法交叉验证

4.留P法交叉验证

5.其他交叉验证

模型调参

调参的概念

1
2
3
4
5
 1.参数分类:
1.1 过程影响类参数: 子模型不变的前提下,调整"子模型数(n_estimators)和学习率(learning_rate)" --> 改变训练过程,提高整体模型的性能
1.2 子模型影响类参数: 调整"最大树深度(max_depth)和分裂条件(criterion)" --> 改变子模型的性能,提高整体模型的性能
1.3 bagging: 降低方差
1.4 boosting: 降低偏差

参数的影响

参数对Random Forest的影响

参数对Gradient Tree Boosting的影响

学习曲线

验证曲线

赛题模型验证和调参

模型过拟合与欠拟合

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
import numpy as np
import pandas as pd
import matplotlib.pyplot as plt
import seaborn as sns
from sklearn import preprocessing
from sklearn.preprocessing import MinMaxScaler
from scipy import stats
from sklearn.decomposition import PCA
from sklearn.model_selection import train_test_split
from sklearn.linear_model import LinearRegression #线性回归
from sklearn.neighbors import KNeighborsRegressor #K近邻回归
from sklearn.tree import DecisionTreeRegressor #决策树回归
from sklearn.ensemble import RandomForestRegressor #随机森林回归
from sklearn.svm import SVR # 支持向量回归
import lightgbm as lgb # LightGBM模型
from sklearn.model_selection import train_test_split # 切分数据
from sklearn.metrics import mean_squared_error #均方误差
from sklearn.metrics import mean_absolute_error #平均绝对值误差
from math import sqrt #平方根
from sklearn.metrics import r2_score #R平方值
from sklearn.model_selection import learning_curve
from sklearn.model_selection import ShuffleSplit
from sklearn.pipeline import Pipeline
from sklearn.preprocessing import PolynomialFeatures
from sklearn.preprocessing import StandardScaler
from sklearn.linear_model import SGDRegressor
#1.读取数据
train_data_file = "zhengqi_train.txt"
test_data_file = "zhengqi_test.txt"
train_data = pd.read_csv(train_data_file, sep='\t', encoding='utf-8') #训练集数据共有2888个样本(V0-V37共38个特征变量) -- 有target字段
test_data = pd.read_csv(test_data_file, sep='\t', encoding='utf-8') #测试集数据共有1925个样本(V0-V37共有38个特征变量) -- 无target字段

#2.归一化(最大值和最小值) --放缩到(0,1区间)
features_columns=[col for col in train_data.columns if col not in ['target']] #从V0到V37
min_max_scaler=preprocessing.MinMaxScaler().fit(train_data[features_columns])

train_data_scaler=min_max_scaler.transform(train_data[features_columns])
test_data_scaler=min_max_scaler.transform(test_data[features_columns])

train_data_scaler=pd.DataFrame(train_data_scaler) #将训练集数据弄成DF格式
train_data_scaler.columns=features_columns

test_data_scaler=pd.DataFrame(test_data_scaler) #将测试集数据弄成DF格式
test_data_scaler.columns=features_columns

train_data_scaler['target'] = train_data['target']

#3.PCA处理
### 1.sklearn.decomposition.PCA PCA处理之后可保持90%的信息数据
pca=PCA(n_components=16) # 整数表示保留几个特征 小数表示百分之多少的信息
#获得转换器
new_train_pca_16=pca.fit_transform(train_data_scaler.iloc[:,0:-1])
new_test_pca_16=pca.transform(test_data_scaler)
#转移为DF格式
new_train_pca_16=pd.DataFrame(new_train_pca_16)
new_test_pca_16=pd.DataFrame(new_test_pca_16)
new_train_pca_16['target']=train_data_scaler['target'] # PCA处理之后保留了16个主成分

#4.切分数据(训练集--> 80%训练集和20%验证数据)
new_train_pca_16=new_train_pca_16.fillna(0) #采用PCA保留16维特征的数据
train=new_train_pca_16[new_test_pca_16.columns]
target=new_train_pca_16['target']
##切分数据 训练数据80% 验证数据20%
train_data,test_data,train_target,test_target=train_test_split(train,target,test_size=0.2,random_state=0)

#5.欠拟合(没有多项式转换)
clf=SGDRegressor(max_iter=500,tol=1e-2) # max_iter表示是训练数据的最大传递次数 tol是停止标准
clf.fit(train_data,train_target)
score_train=mean_squared_error(train_target,clf.predict(train_data)) # 训练集的均方误差
score_test=mean_squared_error(test_target,clf.predict(test_data)) # 测试集的均方误差
print("SGDRegressor train MSE:",score_train) # SGDRegressor train MSE:0.14152723650374396
print("SGDRegressor test MSE:",score_test) # SGDRegressor test MSE:0.1470304756084494

#6.过拟合(多项式转换系数过大)
poly=PolynomialFeatures(5) #多项式转换 写5
train_data_poly=poly.fit_transform(train_data)
test_data_poly=poly.transform(test_data)
clf=SGDRegressor(max_iter=1000,tol=1e-3) # max_iter表示是训练数据的最大传递次数 tol是停止标准
clf.fit(train_data_poly, train_target) #装在转换器
score_train = mean_squared_error(train_target, clf.predict(train_data_poly))
score_test = mean_squared_error(test_target, clf.predict(test_data_poly))
print("SGDRegressor train MSE:",score_train) # SGDRegressor train MSE: 0.1332651075687169
print("SGDRegressor test MSE:",score_test) # SGDRegressor test MSE: 0.14544120121194679

#7.正常拟合
poly=PolynomialFeatures(3) #多项式转换 写3
train_data_poly=poly.fit_transform(train_data)
test_data_poly=poly.transform(test_data)
clf=SGDRegressor(max_iter=1000,tol=1e-3) # max_iter表示是训练数据的最大传递次数 tol是停止标准
clf.fit(train_data_poly, train_target) #装在转换器
score_train = mean_squared_error(train_target, clf.predict(train_data_poly))
score_test = mean_squared_error(test_target, clf.predict(test_data_poly))
print("SGDRegressor train MSE:",score_train) # SGDRegressor train MSE: 0.13343001175858962
print("SGDRegressor test MSE:",score_test) # SGDRegressor test MSE: 0.14179907981584394

模型正则化

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
import numpy as np
import pandas as pd
import matplotlib.pyplot as plt
import seaborn as sns
from sklearn import preprocessing
from sklearn.preprocessing import MinMaxScaler
from scipy import stats
from sklearn.decomposition import PCA
from sklearn.model_selection import train_test_split
from sklearn.linear_model import LinearRegression #线性回归
from sklearn.neighbors import KNeighborsRegressor #K近邻回归
from sklearn.tree import DecisionTreeRegressor #决策树回归
from sklearn.ensemble import RandomForestRegressor #随机森林回归
from sklearn.svm import SVR # 支持向量回归
import lightgbm as lgb # LightGBM模型
from sklearn.model_selection import train_test_split # 切分数据
from sklearn.metrics import mean_squared_error #均方误差
from sklearn.metrics import mean_absolute_error #平均绝对值误差
from math import sqrt #平方根
from sklearn.metrics import r2_score #R平方值
from sklearn.model_selection import learning_curve
from sklearn.model_selection import ShuffleSplit
from sklearn.pipeline import Pipeline
from sklearn.preprocessing import PolynomialFeatures
from sklearn.preprocessing import StandardScaler
from sklearn.linear_model import SGDRegressor
#1.读取数据
train_data_file = "zhengqi_train.txt"
test_data_file = "zhengqi_test.txt"
train_data = pd.read_csv(train_data_file, sep='\t', encoding='utf-8') #训练集数据共有2888个样本(V0-V37共38个特征变量) -- 有target字段
test_data = pd.read_csv(test_data_file, sep='\t', encoding='utf-8') #测试集数据共有1925个样本(V0-V37共有38个特征变量) -- 无target字段


#2.归一化(最大值和最小值) --放缩到(0,1区间)
features_columns=[col for col in train_data.columns if col not in ['target']] #从V0到V37
min_max_scaler=preprocessing.MinMaxScaler().fit(train_data[features_columns])

train_data_scaler=min_max_scaler.transform(train_data[features_columns])
test_data_scaler=min_max_scaler.transform(test_data[features_columns])

train_data_scaler=pd.DataFrame(train_data_scaler) #将训练集数据弄成DF格式
train_data_scaler.columns=features_columns

test_data_scaler=pd.DataFrame(test_data_scaler) #将测试集数据弄成DF格式
test_data_scaler.columns=features_columns

train_data_scaler['target'] = train_data['target']

#3.PCA处理
### 1.sklearn.decomposition.PCA PCA处理之后可保持90%的信息数据
pca=PCA(n_components=16) # 整数表示保留几个特征 小数表示百分之多少的信息
#获得转换器
new_train_pca_16=pca.fit_transform(train_data_scaler.iloc[:,0:-1])
new_test_pca_16=pca.transform(test_data_scaler)
#转移为DF格式
new_train_pca_16=pd.DataFrame(new_train_pca_16)
new_test_pca_16=pd.DataFrame(new_test_pca_16)
new_train_pca_16['target']=train_data_scaler['target'] # PCA处理之后保留了16个主成分

#4.切分数据(训练集--> 80%训练集和20%验证数据)
new_train_pca_16=new_train_pca_16.fillna(0) #采用PCA保留16维特征的数据
train=new_train_pca_16[new_test_pca_16.columns]
target=new_train_pca_16['target']
##切分数据 训练数据80% 验证数据20%
train_data,test_data,train_target,test_target=train_test_split(train,target,test_size=0.2,random_state=0)

#8.模型正则化
##8.1 L2范数正则化
poly=PolynomialFeatures(3) #多项式转换 写3
train_data_poly=poly.fit_transform(train_data)
test_data_poly=poly.transform(test_data)
clf=SGDRegressor(max_iter=1000,tol=1e-3,penalty='L2',alpha=0.0001) # max_iter表示是训练数据的最大传递次数 tol是停止标准
clf.fit(train_data_poly, train_target) #装在转换器
score_train = mean_squared_error(train_target, clf.predict(train_data_poly))
score_test = mean_squared_error(test_target, clf.predict(test_data_poly))
print("SGDRegressor train MSE:",score_train) # SGDRegressor train MSE: 0.13343001175858962
print("SGDRegressor test MSE:",score_test) # SGDRegressor test MSE: 0.14179907981584394

##8.2 L1范数正则化
poly=PolynomialFeatures(3) #多项式转换 写3
train_data_poly=poly.fit_transform(train_data)
test_data_poly=poly.transform(test_data)
clf=SGDRegressor(max_iter=1000,tol=1e-3,penalty='L1',alpha=0.0001) # max_iter表示是训练数据的最大传递次数 tol是停止标准
clf.fit(train_data_poly, train_target) #装在转换器
score_train = mean_squared_error(train_target, clf.predict(train_data_poly))
score_test = mean_squared_error(test_target, clf.predict(test_data_poly))
print("SGDRegressor train MSE:",score_train) # SGDRegressor train MSE: 0.1347595438689653
print("SGDRegressor test MSE:",score_test) # SGDRegressor test MSE: 0.14295179346699013

##8.3 ElasticNet联合L1和L2范数加权正则化
poly=PolynomialFeatures(3) #多项式转换 写3
train_data_poly=poly.fit_transform(train_data)
test_data_poly=poly.transform(test_data)
clf=SGDRegressor(max_iter=1000,tol=1e-3,penalty='elasticnet',l1_ratio=0.9,alpha=0.0001) # max_iter表示是训练数据的最大传递次数 tol是停止标准
clf.fit(train_data_poly, train_target) #装在转换器
score_train = mean_squared_error(train_target, clf.predict(train_data_poly))
score_test = mean_squared_error(test_target, clf.predict(test_data_poly))
print("SGDRegressor train MSE:",score_train) # SGDRegressor train MSE: 0.13501686392085374
print("SGDRegressor test MSE:",score_test) # SGDRegressor test MSE: 0.14315710816572816

模型交叉验证(四种)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
import numpy as np
import pandas as pd
import matplotlib.pyplot as plt
import seaborn as sns
from sklearn import preprocessing
from sklearn.preprocessing import MinMaxScaler #归一化
from scipy import stats
from sklearn.decomposition import PCA #PCA主成分降维
from sklearn.model_selection import train_test_split
from sklearn.linear_model import LinearRegression #线性回归
from sklearn.neighbors import KNeighborsRegressor #K近邻回归
from sklearn.tree import DecisionTreeRegressor #决策树回归
from sklearn.ensemble import RandomForestRegressor #随机森林回归
from sklearn.svm import SVR # 支持向量回归
import lightgbm as lgb # LightGBM模型
from sklearn.model_selection import train_test_split # 切分数据
from sklearn.metrics import mean_squared_error #均方误差
from sklearn.metrics import mean_absolute_error #平均绝对值误差
from math import sqrt #平方根
from sklearn.metrics import r2_score #R平方值
from sklearn.model_selection import learning_curve
from sklearn.model_selection import ShuffleSplit
from sklearn.pipeline import Pipeline #管道
from sklearn.preprocessing import PolynomialFeatures #多项式转变
from sklearn.preprocessing import StandardScaler #标准化
from sklearn.linear_model import SGDRegressor #随机递推下降
from sklearn.model_selection import KFold #KFold是K折交叉验证
from sklearn.model_selection import LeaveOneOut #留一法
from sklearn.model_selection import LeavePOut #留P法
#1.读取数据
train_data_file = "zhengqi_train.txt"
test_data_file = "zhengqi_test.txt"
train_data = pd.read_csv(train_data_file, sep='\t', encoding='utf-8') #训练集数据共有2888个样本(V0-V37共38个特征变量) -- 有target字段
test_data = pd.read_csv(test_data_file, sep='\t', encoding='utf-8') #测试集数据共有1925个样本(V0-V37共有38个特征变量) -- 无target字段

#2.归一化(最大值和最小值) --放缩到(0,1区间)
features_columns=[col for col in train_data.columns if col not in ['target']] #从V0到V37
min_max_scaler=preprocessing.MinMaxScaler().fit(train_data[features_columns])

train_data_scaler=min_max_scaler.transform(train_data[features_columns])
test_data_scaler=min_max_scaler.transform(test_data[features_columns])

train_data_scaler=pd.DataFrame(train_data_scaler) #将训练集数据弄成DF格式
train_data_scaler.columns=features_columns

test_data_scaler=pd.DataFrame(test_data_scaler) #将测试集数据弄成DF格式
test_data_scaler.columns=features_columns

train_data_scaler['target'] = train_data['target']

#3.PCA处理
### 1.sklearn.decomposition.PCA PCA处理之后可保持90%的信息数据
pca=PCA(n_components=16) # 整数表示保留几个特征 小数表示百分之多少的信息
#获得转换器
new_train_pca_16=pca.fit_transform(train_data_scaler.iloc[:,0:-1])
new_test_pca_16=pca.transform(test_data_scaler)
#转移为DF格式
new_train_pca_16=pd.DataFrame(new_train_pca_16)
new_test_pca_16=pd.DataFrame(new_test_pca_16)
new_train_pca_16['target']=train_data_scaler['target'] # PCA处理之后保留了16个主成分

#4.切分数据(训练集--> 80%训练集和20%验证数据)
new_train_pca_16=new_train_pca_16.fillna(0) #采用PCA保留16维特征的数据
train=new_train_pca_16[new_test_pca_16.columns]
target=new_train_pca_16['target']
##切分数据 训练数据80% 验证数据20%
train_data,test_data,train_target,test_target=train_test_split(train,target,test_size=0.2,random_state=0)

#5.模型交叉验证
##5.1 简单交叉验证
clf=SGDRegressor(max_iter=1000,tol=1e-3) # max_iter表示是训练数据的最大传递次数 tol是停止标准
clf.fit(train_data,train_target) #装在转换器
score_train = mean_squared_error(train_target, clf.predict(train_data))
score_test = mean_squared_error(test_target, clf.predict(test_data))
#print("SGDRegressor train MSE:",score_train) # SGDRegressor train MSE: 0.1415415271798254
#print("SGDRegressor test MSE:",score_test) # SGDRegressor test MSE: 0.147046507243961

##5.2 k折交叉验证
kf=KFold(n_splits=5)
for k,(train_index,test_index) in enumerate(kf.split(train)):
train_data,test_data,train_target,test_target=train.values[train_index],train.values[test_index],target[train_index],target[test_index]
clf = SGDRegressor(max_iter=1000,tol=1e-3) # max_iter表示是训练数据的最大传递次数 tol是停止标准
clf.fit(train_data,train_target)
score_train = mean_squared_error(train_target, clf.predict(train_data))
score_test = mean_squared_error(test_target, clf.predict(test_data))
print(k,"折","SGDRegressor train MSE:",score_train) # x 折 SGDRegressor train MSE: 0.1415415271798254
print(k,"折","SGDRegressor test MSE:",score_test) # x 折 SGDRegressor train MSE: 0.1415415271798254

##5.3 留一法 LOO CV
loo=LeaveOneOut()
num=100
for k,(train_index,test_index) in enumerate(loo.split(train)):
train_data,test_data,train_target,test_target = train.values[train_index],train.values[test_index],target[train_index],target[test_index]
clf = SGDRegressor(max_iter=1000,tol=1e-3) # max_iter表示是训练数据的最大传递次数 tol是停止标准
clf.fit(train_data,train_target)
score_train = mean_squared_error(train_target, clf.predict(train_data))
score_test = mean_squared_error(test_target, clf.predict(test_data))
print(k,"个","SGDRegressor train MSE:",score_train)
print(k,"个","SGDRegressor test MSE:",score_test)
if k >= 9:
break

##5.4 留P法 LPO CV
lpo=LeavePOut(p=10)
num=100
for k,(train_index, test_index) in enumerate(lpo.split(train)):
train_data,test_data,train_target,test_target = train.values[train_index],train.values[test_index],target[train_index],target[test_index]
clf = SGDRegressor(max_iter=1000,tol=1e-3) # max_iter表示是训练数据的最大传递次数 tol是停止标准
clf.fit(train_data, train_target)
score_train = mean_squared_error(train_target, clf.predict(train_data))
score_test = mean_squared_error(test_target, clf.predict(test_data))
print(k,"10个","SGDRegressor train MSE:",score_train)
print(k,"10个","SGDRegressor test MSE:",score_test)
if k >= 9:
break

模型超参空间及调参

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
import numpy as np
import pandas as pd
import matplotlib.pyplot as plt
import seaborn as sns
from sklearn import preprocessing
from sklearn.preprocessing import MinMaxScaler #归一化
from scipy import stats
from sklearn.decomposition import PCA #PCA主成分降维
from sklearn.model_selection import train_test_split
from sklearn.linear_model import LinearRegression #线性回归
from sklearn.neighbors import KNeighborsRegressor #K近邻回归
from sklearn.tree import DecisionTreeRegressor #决策树回归
from sklearn.ensemble import RandomForestRegressor #随机森林回归
from sklearn.svm import SVR # 支持向量回归
import lightgbm as lgb # LightGBM模型
from sklearn.model_selection import train_test_split # 切分数据
from sklearn.metrics import mean_squared_error #均方误差
from sklearn.metrics import mean_absolute_error #平均绝对值误差
from math import sqrt #平方根
from sklearn.metrics import r2_score #R平方值
from sklearn.model_selection import learning_curve
from sklearn.model_selection import ShuffleSplit
from sklearn.pipeline import Pipeline #管道
from sklearn.preprocessing import PolynomialFeatures #多项式转变
from sklearn.preprocessing import StandardScaler #标准化
from sklearn.linear_model import SGDRegressor #随机递推下降
from sklearn.model_selection import KFold #KFold是K折交叉验证
from sklearn.model_selection import LeaveOneOut #留一法
from sklearn.model_selection import LeavePOut #留P法
from sklearn.model_selection import GridSearchCV #网格搜索
from sklearn.model_selection import RandomizedSearchCV
#1.读取数据
train_data_file = "zhengqi_train.txt"
test_data_file = "zhengqi_test.txt"
train_data = pd.read_csv(train_data_file, sep='\t', encoding='utf-8') #训练集数据共有2888个样本(V0-V37共38个特征变量) -- 有target字段
test_data = pd.read_csv(test_data_file, sep='\t', encoding='utf-8') #测试集数据共有1925个样本(V0-V37共有38个特征变量) -- 无target字段

#2.归一化(最大值和最小值) --放缩到(0,1区间)
features_columns=[col for col in train_data.columns if col not in ['target']] #从V0到V37
min_max_scaler=preprocessing.MinMaxScaler().fit(train_data[features_columns])

train_data_scaler=min_max_scaler.transform(train_data[features_columns])
test_data_scaler=min_max_scaler.transform(test_data[features_columns])

train_data_scaler=pd.DataFrame(train_data_scaler) #将训练集数据弄成DF格式
train_data_scaler.columns=features_columns

test_data_scaler=pd.DataFrame(test_data_scaler) #将测试集数据弄成DF格式
test_data_scaler.columns=features_columns

train_data_scaler['target'] = train_data['target']

#3.PCA处理
### 1.sklearn.decomposition.PCA PCA处理之后可保持90%的信息数据
pca=PCA(n_components=16) # 整数表示保留几个特征 小数表示百分之多少的信息
#获得转换器
new_train_pca_16=pca.fit_transform(train_data_scaler.iloc[:,0:-1])
new_test_pca_16=pca.transform(test_data_scaler)
#转移为DF格式
new_train_pca_16=pd.DataFrame(new_train_pca_16)
new_test_pca_16=pd.DataFrame(new_test_pca_16)
new_train_pca_16['target']=train_data_scaler['target'] # PCA处理之后保留了16个主成分

#4.切分数据(训练集--> 80%训练集和20%验证数据)
new_train_pca_16=new_train_pca_16.fillna(0) #采用PCA保留16维特征的数据
train=new_train_pca_16[new_test_pca_16.columns]
target=new_train_pca_16['target']
##切分数据 训练数据80% 验证数据20%
train_data,test_data,train_target,test_target=train_test_split(train,target,test_size=0.2,random_state=0)

#5.模型超参空间及调参
##5.1 穷举网格搜索
randomForestRegressor=RandomForestRegressor()
parameters={
'n_estimators':[50,100,200], #预测器数量
'max_depth':[1,2,3] #最大深度
}
clf=GridSearchCV(randomForestRegressor,parameters,cv=5) # cv指定几折交叉验证(训练集中训练集和验证集的划分有几次,然后得出平均值)
clf.fit(train_data,train_target)
score_test = mean_squared_error(test_target, clf.predict(test_data)) #均方误差
print("RandomForestRegressor GridSearchCV test MSE:",score_test) # 0.25522816178256824
##5.2 随机参数优化
randomForestRegressor = RandomForestRegressor()
parameters = {
'n_estimators':[50, 100, 200, 300], #预测器数量
'max_depth':[1, 2, 3, 4, 5] #最大深度
}
clf=RandomizedSearchCV(randomForestRegressor,parameters,cv=5)
clf.fit(train_data,train_target)
score_test = mean_squared_error(test_target, clf.predict(test_data)) #均方误差
print("RandomForestRegressor RandomizedSearchCV test MSE:",score_test) #
print(sorted(clf.cv_results_))
##5.3 LGB调参(使用数据训练LGB模型,采用网格搜索方法调参)
clf=lgb.LGBMRegressor(num_leaves=31)
parameters = {
'learning_rate': [0.01, 0.1, 1], #学习率
'n_estimators': [20, 40] #预测器数量
}
clf=GridSearchCV(clf,parameters,cv=5)
clf.fit(train_data,train_target)
print('Best parameters found by grid search are:',clf.best_params_) #最好的学习率和预测器个数
score_test=mean_squared_error(test_target,clf.predict(test_data))
print("LGBMRegressor RandomizedSearchCV test MSE:",score_test) # LGBMRegressor RandomizedSearchCV test MSE: 0.15175110081465454

特征优化

特征优化的方法

赛题特征优化

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
import numpy as np
import pandas as pd
import matplotlib.pyplot as plt
import seaborn as sns
from sklearn import preprocessing
from sklearn.preprocessing import MinMaxScaler #归一化
from scipy import stats
from sklearn.decomposition import PCA #PCA主成分降维
from sklearn.model_selection import train_test_split
from sklearn.linear_model import LinearRegression #线性回归
from sklearn.neighbors import KNeighborsRegressor #K近邻回归
from sklearn.tree import DecisionTreeRegressor #决策树回归
from sklearn.ensemble import RandomForestRegressor #随机森林回归
from sklearn.svm import SVR # 支持向量回归
import lightgbm as lgb # LightGBM模型
from sklearn.model_selection import train_test_split # 切分数据
from sklearn.metrics import mean_squared_error #均方误差
from sklearn.metrics import mean_absolute_error #平均绝对值误差
from math import sqrt #平方根
from sklearn.metrics import r2_score #R平方值
from sklearn.model_selection import learning_curve
from sklearn.model_selection import ShuffleSplit
from sklearn.pipeline import Pipeline #管道
from sklearn.preprocessing import PolynomialFeatures #多项式转变
from sklearn.preprocessing import StandardScaler #标准化
from sklearn.linear_model import SGDRegressor #随机递推下降
from sklearn.model_selection import KFold #KFold是K折交叉验证
from sklearn.model_selection import LeaveOneOut #留一法
from sklearn.model_selection import LeavePOut #留P法
from sklearn.model_selection import GridSearchCV #网格搜索
from sklearn.model_selection import RandomizedSearchCV
#1.读取数据
train_data_file = "zhengqi_train.txt"
test_data_file = "zhengqi_test.txt"
train_data = pd.read_csv(train_data_file, sep='\t', encoding='utf-8') #训练集数据共有2888个样本(V0-V37共38个特征变量) -- 有target字段
test_data = pd.read_csv(test_data_file, sep='\t', encoding='utf-8') #测试集数据共有1925个样本(V0-V37共有38个特征变量) -- 无target字段

#2.特征构造方法
epsilon=1e-5
#组合交叉特征(自行定义) --增加x*x/y log(x)/y等
function_dict = {
'add': lambda x,y: x+y, #加法
'mins': lambda x,y: x-y, #减法
'div': lambda x,y: x/(y+epsilon), #除法
'multi': lambda x,y: x*y #乘法
}

#3.特征构造函数
def auto_features_make(train_data,test_data,function_dict,col_list): #传入训练集、测试集、特征构造方法、list集合
train_data,test_data=train_data.copy(),test_data.copy() #获取训练集和测试集
for i in col_list:
for j in col_list:
for function_name,function in function_dict.items(): #获取四个函数的函数名和函数
for data in [train_data,test_data]: #从训练集和测试集获取数据
function_features=function(data[i],data[j]) # data[i]就是x data[j]就是y
col_function_features='-'.join([i,function_name,j])
data[col_function_features]=function_features
return train_data,test_data

#4.特征降维处理 --- 先构造新特征,然后使用PCA方法对特征进行降维处理
train_data2,test_data2=auto_features_make(train_data,test_data,function_dict,col_list=test_data.columns)
pca=PCA(n_components=500) # 整数表示保留几个特征 小数表示百分之多少的信息
#获得转换器
train_data2_pca=pca.fit_transform(train_data2.iloc[:,0:-1])
test_data2_pca=pca.transform(test_data2)
#转移为DF格式
train_data2_pca=pd.DataFrame(train_data2_pca)
test_data2_pca=pd.DataFrame(test_data2_pca)
train_data2_pca['target']=train_data2['target'] # PCA处理之后保留了16个主成分
X_train2=train_data2[test_data2.columns].values
y_train=train_data2['target']

#5.使用LightGBM模型对新构造的特征进行模型训练和评估

模型融合

模型优化

模型学习曲线

1
2
3
1.欠拟合(高偏差): 模型太简单(没能力学习到样本的底层规律) -- 训练集和测试集的准确率很低
2.过拟合(高方差): 模型太复杂(学习太过) -- 训练集准确率较好 测试集的准确率很低(相差较大)
3.正常拟合

模型融合提升技术

1
2
3
4
1.概念:产生一组个体学习器 --根据某种策略 --> 结合个体学习器,加强模型效果
2.分类:
2.1 个体学习器之间不存在(×)强依赖关系 可以同时生成的并行化方法 --> Bagging方法和随机森林
2.2 个体学习器之间存在(√)强依赖关系 必须串行的序列化方法 --> Boosting方法

Bagging方法

1
2
3
4
1.概念:从训练集中抽样得到每个基模型所需要的子训练集 --> 对所有基模型预测的结果进行综合,产生最终的预测结果
2.Bagging方法采用 --> 自助采样法(Bootstrap sampling)
2.1 m个样本的原始训练集,每次先随机采集一个样本放入采样集,然后将该样本放回
2.2 m个样本(随机采样),所以会得到m个样本的采样集(可以得到多个不同的弱学习器)

随机森林

1
2
3
4
5
1.概念:(对Bagging方法改进)
2.改进之处:
2.1 基本学习器限定为决策树
2.2 决策树学习过程中引入了随机属性选择
2.3 对基决策树的每个结点,先从该结点的属性集合中随机选择一个包含k个属性的子集,然后从这个子集中选择一个最优属性进行划分(就是划分很多小块然后小块里面选个最优属性划分,然后慢慢更新)

Boosting方法

1
2
3
4
5
6
7
8
1.概念:(阶梯状)基模型按照次序一一进行训练
2.基模型的训练集按照某种策略进行一定的转换 --> 所有基模型预测的结果进行线性综合,产生最终预测结果
3.Boosting方法中著名的算法
3.1 AdaBoost算法 :加法模型、损失函数为指数函数、学习算法为前向分布算法
3.2 提升树(Boosting Tree) : 加法模型、基本学习器为决策树、学习算法为前向分布算法 的二分类算法
3.2.1 对于二分类问题: 损失函数为指数函数
3.2.2 对于回归问题: 损失函数为平方误差
3.3 梯度提升树 : (对提升树算法的改进) 可以将损失函数的负梯度在当前模型的值 <--> 残差的近似值

预测结果融合策略

Stacking示意:

1
2
3
4
5
6
7
8
9
10
11
12
13
1.Voting(投票机制): 采用少数服从多数的原则
1.1 硬投票:对多个模型直接进行投票,投票数最多的类 --> 最终被预测的类
1.2 软投票:不同模型设置不同权重,对多个模型直接进行投票,投票数最多的类 --> 最终被预测的类
2.Averaging:将模型结果的平均值 --> 最终的预测值(不同回归方法预测结果波动幅度相差比较大)
3.Ranking:排名平均的方法(如果有权重,就求出n个模型权重比排名之和)
4.Blending:
4.1 先将原始的训练集分为两个部分(训练集 -> 训练集+测试集)
4.2 在第一层中,用70%的数据训练多个模型,然后去预测剩余30%数据的label
4.3 在第二层中,用30%的数据在第一层预测的结果作为新特征继续训练即可
5.Stacking: 用训练好的所有基模型对训练集进行预测
5.1 第j个基模型对第i个训练样本的预测值作为新的训练集中第i个样本的第j个特征值(最后基于新的训练集进行训练)
5.2 同理,预测的过程也要先经过所有基模型的预测形成新的测试集,最后对测试集进行测试
5.3 Stacking是一种分层模型集成框架 -- 第一层由多个基学习器组成(输入为原始训练集) 第二层由第一层基学习器的输出作为训练集进行训练

最终导包汇总

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32

import numpy as np
import pandas as pd
import matplotlib.pyplot as plt
import seaborn as sns
from sklearn import preprocessing
from sklearn.preprocessing import MinMaxScaler #归一化
from scipy import stats
from sklearn.decomposition import PCA #PCA主成分降维
from sklearn.model_selection import train_test_split
from sklearn.linear_model import LinearRegression #线性回归
from sklearn.neighbors import KNeighborsRegressor #K近邻回归
from sklearn.tree import DecisionTreeRegressor #决策树回归
from sklearn.ensemble import RandomForestRegressor #随机森林回归
from sklearn.svm import SVR # 支持向量回归
import lightgbm as lgb # LightGBM模型
from sklearn.model_selection import train_test_split # 切分数据
from sklearn.metrics import mean_squared_error #均方误差
from sklearn.metrics import mean_absolute_error #平均绝对值误差
from math import sqrt #平方根
from sklearn.metrics import r2_score #R平方值
from sklearn.model_selection import learning_curve
from sklearn.model_selection import ShuffleSplit
from sklearn.pipeline import Pipeline #管道
from sklearn.preprocessing import PolynomialFeatures #多项式转变
from sklearn.preprocessing import StandardScaler #标准化
from sklearn.linear_model import SGDRegressor #随机递推下降
from sklearn.model_selection import KFold #KFold是K折交叉验证
from sklearn.model_selection import LeaveOneOut #留一法
from sklearn.model_selection import LeavePOut #留P法
from sklearn.model_selection import GridSearchCV #网格搜索
from sklearn.model_selection import RandomizedSearchCV

×

纯属好玩

扫码支持
扫码打赏,你说多少就多少

打开支付宝扫一扫,即可进行扫码打赏哦

文章目录
  1. 1. 题目基本情况
    1. 1.1. 数据集
  2. 2. 数据探索
    1. 2.1. 理论知识
    2. 2.2. 赛题数据探索
      1. 2.2.1. 导入工具包
      2. 2.2.2. 可视化数据分布
        1. 2.2.2.1. 箱型图(boxplot)
        2. 2.2.2.2. 直方图(distplot)和Q-Q图(probplot)
        3. 2.2.2.3. KDE分布图(核密度估计kdeplot)
        4. 2.2.2.4. 线性回归关系图(regplot)
      3. 2.2.3. 查看特征变量的相关性
        1. 2.2.3.1. 计算相关性系数(data.corr)
        2. 2.2.3.2. 相关热力图(sns.heatmap)
        3. 2.2.3.3. 根据相关系数筛选特征变量(相关性选择/树模型)
        4. 2.2.3.4. Box-Cox变换
  3. 3. 特征工程
    1. 3.1. 特征工程的重要性和处理
    2. 3.2. 数据预处理和特征处理
      1. 3.2.1. 数据预处理(数据采集+数据清洗+数据采样)
        1. 3.2.1.1. 数据采集
        2. 3.2.1.2. 数据清洗
        3. 3.2.1.3. 数据采样
      2. 3.2.2. 特征处理
        1. 3.2.2.1. 标准化(StandardScaler类)
        2. 3.2.2.2. 区间缩放法(MinMaxScaler类)
        3. 3.2.2.3. 归一化(Normalizer类)
        4. 3.2.2.4. 定量特征二值化(Binarizer类)
        5. 3.2.2.5. 定性特征哑编码(OneHotEncoder类)
        6. 3.2.2.6. 缺失值处理(impute库的SimpleImputer类)
        7. 3.2.2.7. 数据转换
    3. 3.3. 特征降维
      1. 3.3.1. 特征选择
      2. 3.3.2. 线性降维
    4. 3.4. 赛题特征工程
      1. 3.4.1. 异常值分析(箱线图找出异常删除异常)
      2. 3.4.2. 归一化(最大值和最小值)
      3. 3.4.3. 查看数据分布(KDE差异较大删除特征)
      4. 3.4.4. 特征相关性(用热力图可视化)
      5. 3.4.5. 特征降维
      6. 3.4.6. 多重共线性分析(statsmodels.stats.outliers_influence.variance_inflation_factor)
      7. 3.4.7. PCA处理(去除数据的多重共线性,并进行降维)
  4. 4. 模型训练
    1. 4.1. 回归和相关模型
    2. 4.2. 赛题模型训练
  5. 5. 模型验证
    1. 5.1. 模型评估的概念和方法
      1. 5.1.1. 欠拟合和过拟合
      2. 5.1.2. 模型的泛化与正则化
      3. 5.1.3. 回归模型的评估指标和调用方法
      4. 5.1.4. 交叉验证
    2. 5.2. 模型调参
      1. 5.2.1. 调参的概念
      2. 5.2.2. 参数的影响
      3. 5.2.3. 网格搜索(Grid Search)
      4. 5.2.4. 学习曲线
      5. 5.2.5. 验证曲线
    3. 5.3. 赛题模型验证和调参
      1. 5.3.1. 模型过拟合与欠拟合
      2. 5.3.2. 模型正则化
      3. 5.3.3. 模型交叉验证(四种)
      4. 5.3.4. 模型超参空间及调参
  6. 6. 特征优化
    1. 6.1. 特征优化的方法
    2. 6.2. 赛题特征优化
  7. 7. 模型融合
    1. 7.1. 模型优化
      1. 7.1.1. 模型学习曲线
      2. 7.1.2. 模型融合提升技术
        1. 7.1.2.1. Bagging方法
        2. 7.1.2.2. 随机森林
        3. 7.1.2.3. Boosting方法
      3. 7.1.3. 预测结果融合策略
  8. 8. 最终导包汇总
,