1.定义
当变量中含有对被解释变量影响不大的解释变量时,可能因为误差平方和的自由度减小而使方差的估计增大,从而影响回归预测的精度,适当的选择一个变量建立一个最优的回归方程十分重要。
逐步回归(Stepwise Regression)的基本思想是将变量逐个引入模型,每引入一个解释变量后都要进行F检验,并对已经选入的解释变量逐个进行t检验,当原来引入的解释变量由于后面解释变量的引入变得不再显著时,则将其删除。以确保每次引入新的变量之前回归方程中只包含显著性变量。这是一个反复的过程,直到既没有显著的解释变量选入回归方程,也没有不显著的解释变量从回归方程中剔除为止。以保证最后所得到的解释变量集是最优的。
依据上述思想,可利用逐步回归筛选并剔除引起多重共线性的变量,其具体步骤如下:先用被解释变量对每一个所考虑的解释变量做简单回归,然后以对被解释变量贡献最大的解释变量所对应的回归方程为基础,再逐步引入其余解释变量。经过逐步回归,使得最后保留在模型中的解释变量既是重要的,又没有严重多重共线性。
2.分类
在逐步回归中,提取哪些变量主要基于的假设是:在线性条件下,哪些变量组合能够解释更多的因变量变异,则将其保留。逐步回归法选择变量的过程包含两个基本步骤:一是从回归模型中剔出经检验不显著的变量,二是引入新变量到回归模型中,常用的逐步型选元法有前向法、后向法、双向法。
Forward selection(前向逐步回归):
向前法的思想是变量由少到多,属于贪心算法,每次增加一个,直至没有可引入的变量为止。具体步骤如下。
-
步骤1:
对 p 个回归自变量 x 1 , x 2 , . . . , x p , x_{1},x_{2},...,x_{p}, x1,x2,...,xp, 分别同因变量 Y Y Y建立一元回归模型
Y = β 0 + β i X i + ϵ , i = 1 , . . . p Y = \beta _{0}+\beta _{i}X_{i}+\epsilon ,i = 1,...p Y=β0+βiXi+ϵ,i=1,...p
计算变量 X i X_{i} Xi,相应的回归系数的 F 检验统计量的值,记为 F 1 ( 1 ) , . . . , F p ( 1 ) F_{1}^{(1)},...,F_{p}^{(1)} F1(1),...,Fp(1),取其中的最大值 F i 1 ( 1 ) F_{i_{1}}^{(1)} Fi1(1),即
F i 1 ( 1 ) = m a x { F 1 ( 1 ) , . . . , F p ( 1 ) } F_{i_{1}}^{(1)} = max\left \{ \right.F_{1}^{(1)},...,F_{p}^{(1)}\left. \right \} Fi1(1)=max{F1(1),...,Fp(1)}
对给定的显著性水平 α \alpha α,记相应的临界值为 F ( 1 ) F^{(1)} F(1), F i 1 ( 1 ) > F ( 1 ) F_{i_{1}}^{(1)}>F^{(1)} Fi1(1)>F(1),则将 X i 1 X_{i_{1}} Xi1引入回归模型,记 I 1 I_{1} I1为选入变量指标集合。 -
步骤2:
建立因变量 Y 与自变量子集 { X i 1 , X 1 } , . . . , { X i 1 , X i 1 − 1 } , { X i 1 , X i 1 = 1 } , . . . , { X i 1 , X p } \left \{X_{i_{1}},X_{1} \right.\left. \right \},...,\left \{X_{i_{1}},X_{i_{1}-1} \right.\left. \right \},\left \{X_{i_{1}},X_{i_{1}=1} \right.\left. \right \},...,\left \{X_{i_{1}},X_{p} \right.\left. \right \} {Xi1,X1},...,{Xi1,Xi1−1},{Xi1,Xi1=1},...,{Xi1,Xp}的二元回归模型(即此回归模型的回归元为二元的),共有 p − 1 p-1 p−1个。计算变量的回归系数 F 检验的统计量值,记为 F k ( 2 ) ( k ∉ I 1 ) F_{k}^{(2)}(k\notin I_{1}) Fk(2)(k∈/I1),选其中最大者,记为 F i 2 ( 2 ) F_{i_{2}}^{(2)} Fi2(2),对应自变量脚标记为 i 2 i_{2} i2,即:
F i 2 ( 2 ) = { F i ( 2 ) , . . . , F i 1 − 1 ( 2 ) , F i 1 + 1 ( 2 ) , . . . , F p ( 2 ) } F_{i_{2}}^{(2)} = \left \{ F_{i}^{(2)},...,F_{i_{1}-1}^{(2)},F_{i_{1}+1}^{(2)},...,F_{p}^{(2)} \right \} Fi2(2)={Fi(2),...,Fi1−1(2),Fi1+1(2),...,Fp(2)}
对给定的显著性水平 α \alpha α,记相应的临界值为 F ( 2 ) F^{(2)} F(2), F i 2 ( 1 ) > F ( 2 ) F_{i_{2}}^{(1)}>F^{(2)} Fi2(1)>F(2),则变量 X i 2 X_{i_{2}} Xi2引入回归模型。否则,终止变量引入过程。 -
步骤3:
考虑因变量对变量子集 { X i 1 , X i 2 , X k } \left \{ X_{i_{1}},X_{i_{2}},X_{k}\right \} {Xi1,Xi2,Xk}的回归重复步骤2。
依此方法重复进行,每次从未引入回归模型的自变量中选取一个,知道经检验没有变量引入为止。
Backward elimination(后向逐步回归)
与 Forward selection 相反,此时,所有变量均放入模型,之后尝试将其中一个自变量从模型中剔除,看整个模型解释因变量的变异是否有显著变化,之后将对残差平方和贡献较小的变量剔除;此过程不断迭代,直到没有自变量符合剔除的条件。
Bidirectional elimination(双向逐步回归)
这种方法相当于将前两种结合起来。可以想象,如果采用第一种方法,每加入一个自变量,可能会使已存在于模型中的变量单独对因变量的解释度减小,当其的作用很小(不显著)时,则可将其从模型中剔除。而第三种方法不是一味的增加变量,而是增加一个后,对整个模型中的所有变量进行检验,剔除作用不显著的变量。最终尽可能得到一个最优的变量组合。
可以想象,这样得到的变量组合,基于当前数据,应该是可以最大程度的解释因变量的变异,但其反面的作用就是会使模型有偏,即所谓的 overfitting 问题;另外,鉴于算法是基于变量解释度来进行特征提取的,当两个变量对因变量的影响相近时,则不免受到较大的噪声影响,使特征提取结果不稳定。
3.实施过程
逐步回归分析的实施过程是每一步都要对已引入回归方程的变量计算其偏回归平方和(即贡献),然后选一个偏回归平方和最小的变量,在预先给定的水平下进行显著性检验,若显著则该变量不必从回归方程中剔除,这时方程中其他几个变量也都不需要剔除(因为其他几个变量的偏回归平方和都大于最小的一个更不需要剔除)。相反,如果不显著,则该变量需要剔除,然后按偏回归平方和由小到大地依次对方程中其他变量进行检验。将对影响不显著的变量全部剔除,保留的都是显著的。接着再对未引入回归方程中的变量分别计算其偏回归平方和,并选其中偏回归方程和最大的一个变量,同样在给定水平下作显著性检验,如果显著则将该变量引入回归方程,这一过程一直持续下去,直到在回归方程中的变量都不能剔除而又无新变量可以引入时为止,这时逐步回归过程结束。
4.案例
R语言下的评分违约预测模型
setwd('C:\\Users\\zhengyang\\Desktop\\违约预测')getwd()
list.files()raw = read.csv('default of credit card clients.csv',row.names = 1,skip = 1)
View(head(raw))
table(raw$default.payment.next.month)####################################################
################ step1:数据基本分析 ################
###########################################################################################################
################ step2:将数据拆分成2份 ################
#######################################################################################################################
################ step3:给train数据集做profiling ################
###############################################################################################################################
################ step4:给train数据集做各分位值 ################
################################################################################################################################
################ step5:对train数据集做单变量分析 ################
#########################################################################################################################################
################ step6:根据前3步对train数据集做recoding ################
##########################################################################################################################
################ step6:相关性分析 ################
########################################################################################################
################ step7:建模--逻辑回归 ################
######################################################
head(train_model)
#######【模型1】#######
model1_glm = glm(default.payment.next.month~.,data = train_model,family = binomial(link = 'logit'))summary_model1_glm = summary(model1_glm);summary_model1_glm #导出模型
model1_glm_df = data.frame(var = row.names(summary_model1_glm$coefficients),summary_model1_glm$coefficients)View(model1_glm_df)write.csv(model1_glm_df,'model1_glm.csv',row.names = F)######################################################
################ step8:stepwise优化 ######################
#############################################################【模型2】#######
library(MASS)
model_sel = stepAIC(model1_glm,direction = 'both')
summary_stepwise = summary(model_sel);summary_stepwise#导出模型
model2_stepwise_df = data.frame(var = row.names(summary_stepwise$coefficients),summary_stepwise$coefficients)View(model2_stepwise_df)
write.csv(model2_stepwise_df,'model2_stepwise.csv',row.names = F)#通过stepwise剔除了6个变量,接下来对剩下的17个变量再次计算相关系数,以及膨胀系数VIF值
model_vif1 = c('rec_LIMIT_BAL','rec_SEX','rec_MARRIAGE','rec_AGE','rec_PAY_0','rec_PAY_2','rec_PAY_3','rec_PAY_4','rec_PAY_5','rec_PAY_6','rec_BILL_AMT2','rec_BILL_AMT4','rec_PAY_AMT1','rec_PAY_AMT2','rec_PAY_AMT3','rec_PAY_AMT4','rec_PAY_AMT6')train_vif1 = train_model[,c("default.payment.next.month",model_vif1)]
str(train_vif1)fit1 = lm(default.payment.next.month~.,data = train_vif1)
summary(fit1)library(car)
vif1 = data.frame(vif(fit1))
var_vif1 = data.frame(var = row.names(vif1),vif1)
View(var_vif1)write.csv(var_vif1,'var_vif_Tried2.csv',row.names = F)
#有7个变量的vif值都超过2
#接下来再看一下这17个变量之间的相关系数
cor_Tried2 = data.frame(cor.table(train_vif1,cor.method = 'pearson'))
correlation_Tried2 = data.frame(var = row.names(cor_Tried2),cor_Tried2[,1:ncol(train_vif1)])View(correlation_Tried2)
write.csv(correlation_Tried2,'correlation_Tried2.csv',row.names = F)#找出相关系数大于0.5的位置
car_df2 = data.frame()
for (i in 3:ncol(correlation_Tried2))
{#print(i)car_index = which(abs(correlation_Tried2[,i])<1 & abs(correlation_Tried2[,i])>0.5)car_index_df = data.frame(car_names = rep(names(correlation_Tried2)[i],times = length(car_index)),index = car_index)car_df2 = rbind(car_df2,car_index_df)
}View(car_df2)
【参考】
-
百度百科 https://baike.baidu.com/item/逐步回归/585832?fr=aladdin
-
Stepwise regression 学习笔记 SealHuang http://sealhuang.github.io/stepwise-regression
对数据分析、机器学习、数据科学、金融风控等感兴趣的小伙伴,需要数据集、代码、行业报告等各类学习资料,可添加微信:wu805686220(记得要备注喔!),也可关注微信公众号:风控圏子(别打错字,是圏子,不是圈子,算了直接复制吧!)

关注公众号后,可联系圈子助手加入如下社群:
- 机器学习风控讨论群(微信群)
- 反欺诈讨论群(微信群)
- python学习交流群(微信群)
- 研习社资料(qq群:102755159)(干货、资料、项目、代码、报告、课件)
相互学习,共同成长。