博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
机器学习之一:线性回归、梯度下降算法
阅读量:7305 次
发布时间:2019-06-30

本文共 5893 字,大约阅读时间需要 19 分钟。

一、预测

先来看看这样一个场景:

假如你手头有一套房子要出售,你咨询了房产中介。中介跟你要了一系列的数据,例如房子面积、位置、楼层、年限等,然后进行一系列计算后,给出了建议的定价。

房产中介是如何帮你定价的?

“中介”通过他多年的“从业”经验,知道哪些因素会影响房子的价格,且知道各自的“影响”有多大,于是在接过“你的房子”时,他就能通过自已的经验计算出“价格”了。

当然,这个价格,不同的中介,得到的也不同。有经验的中介,可以很准确的预测到价格。而经验不足者,可以会有很大的偏差。

注意上面引号内的东西。将引号内的东西做如下抽象:

中介 ——> 模型从业 ——> 学习影响 ——> 权重房子 ——> 样本价格 ——> 输出

这便可以当作是一个线性回归模型。

二、线性回归

线性回归,用于解决数值预测问题。

1、模型假设

假设有一类数据样本\((x,y)\)\(x\) 表示一个样本的特征集\((x_0,x_1,x_2,...,x_n)\)\(y\) 表示该样本的值。

假设 \(y\)\(x\) 之间,存在某种线性关系,那么数学上,可以用如下方程表示:

$

h(x) = \theta_0x_0 + \theta_1x_1 + ...+ \theta_nx_n
$

用矩阵表示为:

$

h_\theta(x) = \theta^TX
$

显然,要确定 \(x\)\(y\) 之间的关系,只需要求解 \(\theta\) 的值便可以。

那么,\(\theta\) 应该怎么求?

2、梯度下降算法

2.1 直观理解梯度下降

上述的问题,归结到求 \(\theta\)

求取 \(\theta\),可否这样处理:先随机定一组 \(\theta\) 值,然后将已知的样本代入模型公式中,得到输出的 \(h\)值,然后与样本 \(y\) 值相比较,若 \(h\)\(y\) 大,就减少 \(\theta\),若 \(h\)\(y\) 小,就增加 \(\theta\)

显然是OK的,但关键是 \(\theta\) 每次要变化多大的量合适?当然了,每次就修改一点点,例如0.00000000001,然后修改了100年,终于得到一个合适的参数,这样理论上也是可以的。

那有没有什么办法,可以让 \(\theta\) “快速的变化”到理想状态呢?

注意引号中的内容——快速的变化,想到什么没?是的,变化率!

数学上来讲,是求导!

用谁对谁求?当然是计算值与y之前误差了。

有了变化率,\(\theta\) 要变大,还是变小?

梯度下降算法认为,往梯度反方向变化,即是做减法。

2.2 梯度下降法计算过程

误差函数

令误差函数如下式:

$

J = \frac{1}{2m} \sum_{i=1}^{m}(h_\theta(x^{(i)})-y^{(i)})^2
$

这个式子,解释一下。

误差用输出值与 \(y\) 值作差,这个没得说。平方是让差值恒为正。而前方的 1/2,是为了求导时将平方约去,简化运算。

求导

\(J\)\(\theta\)偏导数为

$

grad = \frac{1}{m} \sum_{i=1}^{m}(h_\theta(x^{(i)})-y^{(i)})x_j^{(i)}
$

更新\(\theta\)

由梯度下降法,迭代计算\(\theta\)的值,其中\(\alpha\)为学习率

$

\theta_j :=\theta_j - \alpha*grad
$

三、单一特征的线性回归

1、数据可视化

fprintf('Plotting Data ...\n')data = load('ex1data1.txt');X = data(:, 1); y = data(:, 2);m = length(y); % number of training examples% Plot Data% Note: You have to complete the code in plotData.mplotData(X, y);fprintf('Program paused. Press enter to continue.\n');pause;

2、误差函数及测试

2.1、误差函数

根据公式,编写J函数

function J = computeCost(X, y, theta)m = length(y); % number of training examples% J=1/(2*m)*sum((X*theta-y).^2); J=1/(2*m)*(X*theta-y)'*(X*theta-y);end

2.2、测试误差函数

X = [ones(m, 1), data(:,1)]; % Add a column of ones to x (x_0 = 1)theta = zeros(2, 1); % initialize fitting parameters% Some gradient descent settingsiterations = 1500;alpha = 0.01;fprintf('\nTesting the cost function ...\n')% compute and display initial costJ = computeCost(X, y, theta);fprintf('With theta = [0 ; 0]\nCost computed = %f\n', J);fprintf('Expected cost value (approx) 32.07\n');% further testing of the cost functionJ = computeCost(X, y, [-1 ; 2]);fprintf('\nWith theta = [-1 ; 2]\nCost computed = %f\n', J);fprintf('Expected cost value (approx) 54.24\n');fprintf('Program paused. Press enter to continue.\n');pause;

3、梯度下降

3.1、梯度下降算法

根据梯度下降公式,实现算法

function [theta, J_history] = gradientDescent(X, y, theta, alpha, num_iters)m = length(y); % number of training examplesJ_history = zeros(num_iters, 1);  % one columnfor iter = 1:num_iters    grad = 1/m * X'*(X*theta-y);    theta = theta - alpha * grad;     J_history(iter) = computeCost(X, y, theta);endendfprintf('\nRunning Gradient Descent ...\n')% run gradient descenttheta = gradientDescent(X, y, theta, alpha, iterations);% print theta to screenfprintf('Theta found by gradient descent:\n');fprintf('%f\n', theta);fprintf('Expected theta values (approx)\n');fprintf(' -3.6303\n  1.1664\n\n');

3.2、运行梯度下降

传入训练集,计算出theta矩阵

fprintf('\nRunning Gradient Descent ...\n')% run gradient descenttheta = gradientDescent(X, y, theta, alpha, iterations);% print theta to screenfprintf('Theta found by gradient descent:\n');fprintf('%f\n', theta);fprintf('Expected theta values (approx)\n');fprintf(' -3.6303\n  1.1664\n\n');

4、预测

根据计算出来的theta矩阵,预测新的样本对应的值。

% Predict values for population sizes of 35,000 and 70,000predict1 = [1, 3.5] *theta;fprintf('For population = 35,000, we predict a profit of %f\n',...    predict1*10000);    predict2 = [1, 7] * theta;fprintf('For population = 70,000, we predict a profit of %f\n',...    predict2*10000);

四、多特征的线性回归

多特征的线性回归,算法与单一特征基本一样,唯一不同的仅仅是X的特征数量、theta的参数数量。

另外,多特征的样本,各个特征的数据范围可能存在数量级的差别,最后得出的误差函数的等高线可能是一个不规则的图形。而梯度下降,是沿着误差函数的等高线的法向方向进行,对于一个不规则的图形,其法向方向是多变的,这样一来,梯度下降可能每次迭代的方向都会有差别,进而形成震荡,迭代速度也会变慢。

为使算法更快的找到最优解,使用“均值归一化”的进行标准化处理,将样本各个特征的数据,约束在相同的范围内。这样处理后,如果是二维特征,其误差函数的等高线就是一个近圆,梯度下降就直指圆心进行,能更快找到最优解。

1、标准化特征

1.1、 加载数据,并标准化处理

%% Load Datadata = load('ex1data2.txt');X = data(:, 1:2);y = data(:, 3);m = length(y);% Print out some data pointsfprintf('First 10 examples from the dataset: \n');fprintf(' x = [%.0f %.0f], y = %.0f \n', [X(1:10,:) y(1:10,:)]');fprintf('Program paused. Press enter to continue.\n');pause;% Scale features and set them to zero meanfprintf('Normalizing Features ...\n');% 将特征的值,都约束在[-1,1]区间内[X mu sigma] = featureNormalize(X);% Add intercept term to X??X_0 = 1X = [ones(m, 1) X];

1.2、标准化函数(使用均值归一化算法)

计算方法:X_out = (X_in - mu)/sigma,其中,mu为样本均值,sigma为样本标准差

function [X_norm, mu, sigma] = featureNormalize(X)X_norm = X;mu = zeros(1, size(X, 2));   % get the count of columnsigma = zeros(1, size(X, 2));[X_norm,mu,sigma] = zscore(X);end

2、多维特征样本的误差函数、梯度下降算法

与一维样本的公式完全一样。不再详述。

五、正规方程解法

求解theta,除了使用梯度下降法外,还可以直接使用公式,进行计算。

上面讲到,如果是多维数据,在进行梯度下降时,为使计算速度加快,需要将多维特征数据进行标准化处理。而若是使用正规方程解法,则不需要,在原有的样本进行计算即可。

正规方程解法,因为需要求解逆矩阵,在样本数量很大的情况下,其运算速度会非常慢,所以,梯度下降法与正规方程解法,根据数据量的大小,进行选择。

经验数值是,当数据量大于1,000,000时,一般采用梯度下降法。

1、方程解法

function [theta] = normalEqn(X, y)theta = zeros(size(X, 2), 1);theta = pinv(X'*X)*X'*y;end

2、预测

可以看到,正规方程解法,与梯度下降法,得出来的结果很接近。

data = csvread('ex1data2.txt');X = data(:, 1:2);y = data(:, 3);m = length(y);% Add intercept term to XX = [ones(m, 1) X];% Calculate the parameters from the normal equationtheta = normalEqn(X, y);% Display normal equation's resultfprintf('Theta computed from the normal equations: \n');fprintf(' %f \n', theta);fprintf('\n');% Estimate the price of a 1650 sq-ft, 3 br house% ====================== YOUR CODE HERE ======================% price = 0; % You should change thisprice = 1650; % You should change thisprice = [1,1650,3]*theta;

转载于:https://www.cnblogs.com/Fordestiny/p/8534470.html

你可能感兴趣的文章
【总结整理】关于Json的解析,校验和验证
查看>>
<fmt:timeZone/>显示全球时间
查看>>
JAVA数据结构-----栈
查看>>
sonar常见
查看>>
它组对我们组的建议
查看>>
模拟栈的回溯,完全二叉树搜索,(ZOJ1004)
查看>>
Intellij IDEA 创建消息驱动Bean - 接收JMS消息
查看>>
flask笔记(一)
查看>>
ES6学习笔记
查看>>
Spring.NET学习笔记1——控制反转(基础篇)
查看>>
kindeditor之video插件开发
查看>>
ios-表视图-问题
查看>>
Java中原子类的实现
查看>>
数组索引,内容交换
查看>>
第四次实验报告
查看>>
测试计划
查看>>
Visual Studio 常用快捷键
查看>>
(转) java 复制文件,不使用输出流复制,高效率,文件通道的方式复制文件
查看>>
【BZOJ 1861】Book 书架
查看>>
map的使用注意事项
查看>>