Logistic Regression (LR)
Logistic Regression (LR) 理论
简介:LR模型属于广义线性模型的一种,利用logistic函数来进行回归和分类(主要是0/1分类)。步骤是分析具体问题--建立代价函数--通过迭代最优化模型的参数--测试模型好坏
优缺点:LR模型用于分类时能够给出$[0,1]$概率,而不仅是非黑即白的分类结果;运行速度快,主要适用于二分类
1. 模型理论:
Logistic Function:
\[f(z)=\frac{1}{1+e^{-z}}\]
对于线性边界:
\[ z=\theta^Tx=\theta_0x_0+\theta_1x_1+…+\theta_nx_n\]
其中训练数据为$x={[x_0,x_1,x_2,...,x_n]}^T$,模型参数为$\theta^T$
构造预测函数为:
\[h_{\theta}(x)=\frac{1}{1+e^{-\theta^Tx}}\]
上式的$h_{\theta}(x)$表示分类结果取1的概率,因而$1-h_{\theta}(x)$即为分类结果取0的概率
Cost function:
在前面介绍的线性模型中,我们可以用模型误差的平方和来作为代价函数,但是如果在LR中沿用这种代价函数,将会得到一个non-convex function非凸函数。具体参考凸优化。因此我们最好还是选取另外一种合适的代价函数
由$h_{\theta}(x)$的概率意义可以写出式子:
\[P(y|x;\theta)=(h_{\theta}(x))^y(1-h_{\theta}(x))^{1-y} \]
利用the method of maximum likelihood. 取似然函数
\[L(\theta)=\prod_{i=1}^mP(y_i|x_i;\theta)=\prod_{i=1}^m(h_{\theta}(x_i))^{y_i}(1-h_{\theta}(x_i))^{1-y_i} \]
取对数似然函数:
\[l(\theta)=\log{L(\theta)}=\sum_{i=1}^m{y_i}\log{h_{\theta}(x_i)}+{1-y_i}\log(1-h_{\theta}(x_i)) \]
为了方便,我们就取$J(\theta)=-l(\theta)/m$,问题就转化为求$J(\theta)$的最小值
梯度下降算法求解$J(\theta)$最小值:
\[ \theta_j:=\theta_j-\alpha\frac{\partial L(\theta)}{\partial \theta_j} \]
化简得到:
\[ \theta_j:=\theta_j-\alpha\frac{1}{m}\sum_{i=1}^m(h_{\theta}(x_i)-y_i)x_i^j \]
这样的更新规则看起来与线性回复的更新规则形式完全一样,但是由于这里面的预测函数是logistic函数,所以这两种梯度下降的迭代方式是不同的
2. LR在多元分类中的应用
LR主要针对的是二分类,但对于多元分类,可以采用one-vs-all的思路。每次分出一类,重复多次即可
3. Overfitting - Regularization
如上图,对于训练集而言,拟合的非常好。但是这种模型的适用性和预测性都不够好。为了防止这种过拟合的情况发生,我们有以下两种手段:
a. 去掉一些对预测没有意义的特征量,可以根据实际需求手动筛选,或者利用特征将维等手段
b. 正则化,保留所有特征,但减小参数的大小。
这里我们只介绍正则化的方法。正则化的方法可以从代价函数入手,可以加入惩罚项,将代价函数改为如下形式:
\[l(\theta)=\left[-\frac{1}{m}\sum_{i=1}^m{y_i}\log{h_{\theta}(x_i)}+{1-y_i}\log(1-h_{\theta}(x_i))\right]+\frac{\lambda}{2m}\sum_{j=1}^n \theta_j^2 \]
$\lambda$被称为Regularization parameter。我们可以这样理解,大多数过拟合的形成原因是高阶项的贡献,为了减弱高阶项的影响,我们可以加入$x\theta_n$项。当$x$较大时,高阶项的系数$\theta_n$对预测结果的贡献就小了很多。当我们不知道哪几项对过拟合有贡献时,就统一为它们分配一个系数$\lambda$。换个思路,我们利用极限来设想$\lambda$非常大,那么为了使代价函数减小,不得不设定$\theta^T=0$,这样我们得到的拟合曲线就变成了最简单的直线。这也体现了$\lambda$对参数$\theta^T$的惩罚作用。
Logistic Regression (LR) 实践
1 import pandas as pd 2 import statsmodels.api as sm 3 import pylab as pl 4 import numpy as np 5 #导入数据 6 df=pd.read_csv("http://www.ats.ucla.edu/stat/data/binary.csv") 7 #更改columns 8 df.columns=["admit","gre","gpa","prestige"] 9 print (df.columns) 10 #显示prestige与admin的数据关系 11 print (pd.crosstab(df['admit'],df['prestige'],rownames=['admit'])) 12 #show 四种特征参量的直方图 13 df.hist() 14 15 #虚拟变量(dummy variables) 16 #通过构造0/1型的变量来属性化参量 17 dummy_ranks=pd.get_dummies(df['prestige'],prefix='prestige') 18 print (dummy_ranks.head()) 19 ##数据清洗整合 20 cols_to_keep=['admit','gre','gpa'] 21 data=df[cols_to_keep].join(dummy_ranks.ix[:,'prestige_2':]) 22 print (data.head()) 23 #添加logistic回归所需的intercept变量 24 data['intercept']=1.0 25 #训练集要留出一个虚拟变量作为基准 26 train_cols=data.columns[1:] 27 28 #logisti回归的参数拟合 29 logit=sm.Logit(data['admit'],data[train_cols]) 30 result=logit.fit() 31 32 #预测数据 33 import copy 34 combos=copy.deepcopy(data) 35 predict_cols=combos.columns[1:] 36 combos['intercept']=1.0 37 combos['predict']=result.predict(combos[predict_cols]) 38 39 #准确度检验 40 total=0 41 hit=0 42 for value in combos.values: 43 predict=value[-1] 44 admit=int(value[0]) 45 #预测被录取的数目total 46 if predict>0.5: 47 total+=1 48 #的确被录取的数目hit 49 if admit==1: 50 hit+=1 51 52 print ('Total:%d,Hit:%d,Precision:%.2f'%(total,hit,100.0*hit/total))
admit/gpa/gre/prestige 的统计分布
结果的准确率达到$61.22%$
输入" print result.summary() " 可以查看拟合结果
这里就直接把Python现成的包拿来用,只是学习了Python的使用。对具体算法的熟悉还要参看Ng的公开课作业
总结:Logistic函数在非线性科学中常有应用,良好的0/1特性可以拿来应对各种分类问题。常见的例子还有预测肿瘤/房价等。在LR之前,没有总结线性回归是因为两者相似处很多,并且LR更常用一些。其中的一些问题其实还没有很好的理解:凸优化/其他优化方式。等会了再填坑。