Logistic 回归101
本文作者时新加坡国立大学的数学博士,来自作者的个人公众号 Optimization邂逅Statistics 欢迎订阅,查看更多原创机器学习入门好文
小编的号:今天有人问我机器学习的入门方法,我答道,先看懂原理(如果数学基础好的化),如果一时看不懂, 不管什么编程语言,先跑通样例数据,之后改数据,该方法的参数,看看不同的参数下的图会是怎样,之后再去看方法,想清楚为什么会有这样的改变。今天的文章正是这样的一个学习案例。
下面是正文===================================================
今天,我们将开始聊一聊机器学习的一类重要问题——分类。
我们今天将聊一聊其中最简单,也是在实际中应用地最广的二分类算法:Logistic 回归。
作为开通原创保护后给大家的第一波福利,最后送上用 Matlab 实现的代码以及其在一个小例子上的表现。
走进分类的世界
分类是机器学习最重要的任务之一,也是机器学习应用地最成功的领域(之一)。我们常见的很多问题,其本质都是分类问题。首先,我们来看一个简单的例子。
识别问题
这个例子是大牛Lecun 的一个经典工作,早在上世纪八九十年代,Lecun 通过神经网络已经取得了比较高的手写数字识别准确率。
手写数字识别的目标,是对于一张给定的带有手写数字的输入图片,我们需要识别出上面的数字是几,换句话说,我们需要知道一张带有数字的图片属于0到9这十个类中的哪一类。
下面,我们从数学的角度来描述一下这个问题。
我们用一个矩阵变量 X 表示输入图片的灰度值,我们的目标, 是能构造一个分类器(classifier) f, 使得 f(X) 取 0 到 9 这10个值中的一个。
也就是说,我们希望构造一个映射,使得这个映射可以将任何一张写有0到9的数字的图片映射到它所对应的类别。
声明:下面这几段位于分割线间的文字未提交至国家食品安全质量检查机构,请谨慎服用!
分类问题我个人认为大致可以分为两种类型,一是有预设的标识(label),对于新的输入X,我们需要得到其对应的标识 y。第二类是聚类问题(clustering),在聚类问题中,标识是未知的,很多时候,甚至一共有多少类也是未知的,我们的目的,是通过分析输入数据的特征,将最相似的数据聚合到一起。
有一些看似和分类无关的问题,其本质其实也是分类。一个常见的问题是图像分割。图像分割的目的是将一幅图像分为前景和背景。图像分割中主要有两种情形,一种情形是将用户的简单交互和图像同时作为输入,这种情形下,更像一个分类问题(用户对很小一部分像素进行了标记);另一种情形下,我们单纯地将图像作为输入,却没有用户交互的信息。这种情形下,基于单张图片进行图片分割显得比较困难,一种常见的做法是通过将多张相似的图片一起进行协同分割(co-segmentation). 在这种情况下,我们实质上在对图像进行聚类。
看完上面这段话,有不少读者可能觉得
为什么单张无标记图片分割不了,几张相似的无标记图片放在一起反而可以进行分割了???图片越多难道不应该越难吗???
我们不妨先卖个关子,简单的解释在下期推送中呈现,嘿嘿。
Logistc 回归
今天,我们首先聊一聊最简单的分类问题——二分类问题。二分类问题并不是要看看谁比较“二”, 纯粹只是把数据分为两类。
既然我们上个系列详细地聊了聊线性回归模型,我们首先来聊一聊最重要的线性二分类器之一—— logistic 回归模型。
在这篇杂谈中,我们假设数据是线性可分离的,也就是说,存在一条线性边界,将(绝大部分)数据分为两部分。这个条件其实是很苛刻的,很多数据都不满足这个假设。但是,深入研究线性分类器仍然是十分重要的,在我们后续的杂谈中,我们可以看到我们可以通过简单的线性分类器构造出复杂的决策边界(decision boundary)(例如boosting)。
由于我们考虑二分类问题,因此,我们假设输出变量(标识)y 的取值为{0, 1} 这两个离散的值. 一种直观的想法是,我们能不能直接基于我们之前讨论的线性模型来进行分类?
一部分读者心中甚至还有了一个很“完美”的方案,基于之前的线性回归模型,如果 y > 0 则为第一类,否则则为第二类。然而,对于这种看起来切实可行的方案,我们却总能构造出一些表现的不好的例子。但是,这种思想是非常好的,为了直观,我们把上述的思想用一幅图像来表达
这其实就是集合 {x>0} 的示性函数(indicator function)所对应的图像。
其实,logistic 回归的思想和上述有近乎雷同的地方,但是,直观上来说,我们并不希望我们的输出变量y 能取到小于0或者大于1的值。于是,我们有了如下的假设
其中,函数
是不是觉得自己发现了什么很厉害的事情?
其实,你会发现其中的思想其实几乎是一样的,但是,这两种模型却有着本质的区别,关于logistic 回归假设的合理性,我们会在聊“生成线性回归模型”的时候有更深刻的认识。
注意到,当z 趋于正无穷的时候,g(z)的值趋于1, 而当z趋于负无穷的时候,g 的值将趋于0.
考虑到logistic 回归与我们之前提到的思想的“雷同”性,我们知道,决策边界应该是 g 的值为 0.5 时所对应的线性边界。
模型参数的确定(Training)
下面,我们来聊一聊怎样训练模型参数。回顾一下,在线性回归模型中,我们通过极小二乘构造了一个费用函数(cost function) J, 通过极小化费用函数,我们得以训练模型参数。
但是,在线性回归的系列杂谈中我们聊过,费用函数 J 的合理性,来源于极大似然!!!
因此,在训练logistic 回归模型的参数时,我们不能机械地照搬在线性回归模型中所构造的费用函数,而应该构造logistic 回归模型对应的似然函数,通过极大化似然函数来构造费用函数!
由于我们构造的假设
于是,我们有
对于m个给定的独立同分布的训练样本
logistic 回归所对应的似然函数为
和我们曾经讨论过的一样,我们通过取对数来进行简化,于是,我们得到如下的对数似然函数
于是,我们通过求解如下的优化问题来确定模型参数
由于上述优化问题的Hessian 矩阵是一个对称半负定矩阵,我们用牛顿法进行求解。由于我会贴出一个求解代码,所以我就偷懒不讨论优化求解的部分了。
但是,作为一个负责任的公众平台,当我开始杂谈优化算法的时候,我会特意分析关于logistic 回归模型和带正则项的logistic 回归模型的优化求解算法。
一个简单的例子(Data from Andrew Ng)
下面,我们通过一个简单的例子来看一看logistic 回归的表现。Andrew Ng 在其主讲的 machine learning 课程的作业中,提供了一组测试logistic 回归模型的数据,为了直观起见,我将这组数据画在下图中
其中,红色的 x 代表标识为0的数据,绿色的圆圈代表标识为1的数据,通过运行粘贴在后文中的matlab代码,我们可以得到如下的决策边界
由这个简单的例子可以看出,logistic 给出的决策边界是合理的。
代码
废话不多说了,直接上代码!!!
数据下载链接:https://pan.baidu.com/s/1bpxHLEZ
提取码: 755t
%% This code is to test logistic regression
function logistic_test
%% 读入数据
load ('q1x.dat');
load ('q1y.dat');
%% 预处理数据
q1x=[ones(size(q1x, 1),1) q1x];
%% 获取数据大小
m_x=size(q1x, 1);
n_x = size(q1x, 2);
m_y = size(q1y,1);
if m_x ~= m_y
error('Dimensions not agree.');
end
%% 可视化数据
figure; hold on;
for i=1:m_x
if(q1y(i)==0)
plot(q1x(i,2), q1x(i, 3), 'rx');
else
plot(q1x(i,2), q1x(i, 3), 'go');
end
end
%% 初始化theta
theta = zeros(n_x, 1);
max_iter = 30; % 最大循环次数
tol = 1e-6; % 误差设置
for i=1:max_iter
grad = zeros(n_x, 1);
H = zeros(n_x, n_x);
for j=1:m_x
hxj = sigmoid(q1x(j,:)*theta);
grad = grad + q1x(j, :)'*(q1y(j)-hxj);
H = H - hxj*(1-hxj)*q1x(j, :)'*q1x(j, :);
end
theta = theta - inv(H)*grad;
if norm(grad)<tol
break;
end
end
%% 画出决策边界
x = min(q1x(:, 2)): 0.01:max(q1x(:, 2));
y = -theta(1)/theta(3) - theta(2)/theta(3)*x;
plot(x, y);
xlabel('x1');
ylabel('x2');
end
%% 计算sigmoid 函数
function a = sigmoid(x)
a = 1./(1 + exp(-x));
end
部分内容参考了Andrew Ng 的讲义!
更多阅读