0

CS 231N 斯坦福李飞飞机器视觉课

这个笔记的话,因为本身的课件之间有一些耦合性,但是关联性也不是很大,这里的话,因为我是在雷锋网上看的整个视频课程,感谢字幕组有整理出来每一个Lecture的关键词,这里的话我的笔记组织的话,主要就是以名词为主进行组织:

0.0 Lecture 1

0.1.1 Adaboost 算法

Adaboost是一种迭代的算法,本质上其实是对于一个训练集来训练不同的分类器classifier,然后把这些classifier进行集合,组成一个更强的classifier。其实本质上还是一个级联的过程。

整个算法的话,过程的话其实是:

1、先对于N个训练样本进行学习得到第一个弱分类器;

2、然后把粉错误的样本和新的样本数据一起构成一个新的N个的新的训练样本,对于这个新的样本集合进行学习得到第二个弱分类器;

3、以此类推,每次都把之前所有的classifier分错误的样本+新的样本组成一个N个训练样本集,再通过学习得到后续的分类器;

4、最终的话,我们得到一个强分类器,因此我们的数据被分割成为哪一类是由分类器的权值决定的。

0.0.1 Annotate 标上注释

这里面的话,其实是Li Fei Fei组的一个研究方向,因为我们本身的话希望的是通过自然语言和机器视觉的结合实现,我们看到一幅图片,机器对应生成语言来进行描述图片。

0.0.2 Block World

这里的话,其实是早期学者研究的时候学者对于世界的一种简单建模。

其实很多时候,发现本身的话还是先从图形的边缘特征入手,来构建图像中物体的框架,然后更抽象的就是提取出对应的特征点,然后把整个图像的特征抽象为一个点。

0.0.3 Bounding Box 边界框

在这里的话,其实我们看到Bounding Box的话,是最初的一种图像目标检测的一种方法,一般来说我们想要检测一个目标,不单单是要得到一个分类,更希望能够把物体单独提取出来,这里的话简单的就是拿一个框框出来,这个非常的简单,但是的话,未来想做的是能够直接抠图出来,那就涉及到了图像分割问题。

0.0.4 Convolutional Neural Network 卷积神经网络

卷积神经网路——也就是我们所说的CNN network structure, 是通过构建一个神经网络来进行图像的分类问题。

这里的话,我们使用了这些网络架构,进而可以得到很好的性能提升。上图除了2010还是传统的分类方法之外,2012年之后的都是深度学习的方法。

其实的话,所谓的深度学习本质上只是机器学习的一个子集。所谓的深度Depth其实不是什么新鲜事,仅仅是实现了层级数比较多的神经网络进而进行机器学习而已。

这里的卷积神经网络其实和之前Lecun的手写数字识别模型是非常的类似的。

这里的话,其实可以看出,深度学习也是受益于硬件提升非常的多,如果没有高性能CPU、GPU的出现,那么我们在实现CNN的过程中不会有这么大的提升。

0.0.5 Fully-Connected Layers

这里的我们的fully connected layers主要指的是CNN中的一个特别的层级,在中文中可以被翻译为:全链接层/完全链接层;在CNN中间,我们的Fully-connected Layers主要实现一种功能:通过把学习到了的分布式特征表示来映射到我们的样本标记空间中。其实就相当于我们的CNN之前的步骤做的是特征提取的过程,但是最后的话我们如果想要实现一个分类的过程的话,还是需要Fully-connected layer来进行实现的。

在这里面的话,我们的全链接层的操作可以有卷积层操作实现,常常大家使用的一种方法是借助传统机器学习中的一个神经元的激活方法进行表示全链接的。这里的话,整个全链接的核心操作就是$y = W x$,进而把一个特征空间线性变换到了另一个特征空间中,目标空间中的任意一个维度的话也就会受到源空间的每一个维度的影响,所以说目标向量其实可以是源向量的加权和。

这里的话,我们最后两个fully connected layers主要做的工作就是对于我们的特征做分类,其实这里的话认为我们使用传统的softmax操作也是可以的。

0.0.6 Generalize 泛化

在深度学习(机器学习)中间,其实比较重要的一个概念就是我们想要尽可能的实现模型的generalization,因为我们希望建立一个通用的模型,从而能够对于尽可能多的问题进行我们想要的操作。这里的话不知道我们的人脸方法和其他超分辨率方法能不能有一种泛化模型。

0.0.7 Histogram of Gradient 方向梯度直方图

这是一种可以比较好的表示图片的方法,通过构建一个图片的梯度直方图,能够把整个画面中的相关特征通过统计建模转换成概率模型,这样子的话在我们后面的处理过程中也可以有比较大的提升。

0.0.8 Image formation 图像成像原理

其实这里面的话,并不是完全的研究说成像,而是希望从生物体本身的一种对于图像感知的方法上面得到启发从而构建机器的视觉模型。下面的话我结合PPT中间的一张图像对于人眼成像的原理进行简单的介绍:

1、人眼其实一开始对于图像的话是一个简单感知的过程。在最开始,我们的人眼是有一个叫Primary Visual Corte(初级视觉皮层)的过程,这歌层级的话其实主要就是得到我们第二张的Edge Image,通过我们的Edge Image,我们可以感知到整幅图像边缘信息,从而大概对于物体的轮廓有一个了解。其实我们的超分辨率的话本身也可以归纳成为一个低级视觉的问题。

2、在我们提出出来对应的features之后,我们进一步的就是构建了一个相对的深度等其他信息的结构图,进一步的可以让我们看出来整个图形是什么样子的,这样子的话这些辅助信息的话也可以帮助我们进行物体的辨别;

1.0 Lecture 2

1.0.1 Column Vector

这里的话其实有一个想法:在我们进行图片分类任务的时候,其实如果我想要把整个过程用矩阵进行表示的话,其实就是:
$$Y = W * X$$

在这个公式之中,我们可以理解成:X为我们的输入图像,其中的尺寸是$width * height * channels$的一个三维矩阵(可以看作一个立方体),然后经过一个分类器classifier(广义)之后,我们可以得到对应的输出,这里的输出的话其实是我们自己需要的结果,有的时候可能是一幅图片$width * height *channel$或者是对应的标签(分类问题),这里的话,我们并不是单纯的生成一个标签,而有可能是生成各个标签的权重值的列向量:{cat:1,dog:0.2348294....,car:0.231123123}。这样子的话其实根据我们每一个需要的结果不同,我们乘以的矩阵的维度也是不一样的。这里的话唯一的要求应该就是满足矩阵运算的维度即可。

1.0.2 CLassifier 分类器

这里的话,我们可以看出,如果我们合理的设计我们的分类器,我们其实最简单的想法是通过hard-coding来进行编程,但是单单是识别猫的过程就是非常复杂的,我们没有办法使用人力就写出来,这个时候的话我们其实就希望能不能有别的方法可以从数据中概括出范式,我们只需要解决这个归纳过程就可以了呢?答案是肯定的。很多人都在研究Data-dirven的method来进行图像的分类:

  1. Collect a dataset of images and labels
  2. Use Machine Learning to train a classifier
  3. Evaluate the classifier on new images

这里的话,其实最简单的办法就是使用nearest neighbor的方法对于整个图像特征进行判断,进而看看能不能实现一个简单的分类。其实这个方法的话,用数学方法来表示的话非常的简单:

这里的话,我们首先假设我们的Sampled image(已经标记好为若干分类)为$L_j,其中j = 0,1,2,...,n$,对应的我们需要判断的图像分别为:$I_k, 其中k = 0,1,2,...,m$,我们需要做的操作仅仅是分别计算一下每一个待比较图像$I$和已经分类好的图像$L$之间的距离(像素与像素之间的差值大小),$Score = I_k - L_j$,然后再对于这个Score列向量提取出最大值并且对应到相应的标签就可以完成一个最简单的聚类过程。

这里面的话,引申出来了其他的几个概念,可以在这个简单的聚类过程中进行解答:

1.0.2.1 Comparison function

这里的话,我们的整个比较过程的话,我们是在之前简单的一个$|I_k - L_j|$这个公式完成的。这个公式其实区分能力非常的不好,我们可以选择其他的评价图片与图片之间距离、相似度的函数进行比较,这个函数就可以叫做Comparison Function。

1.0.2.2 Decision Boundaries

在这个聚类结果的图形中,其实我们就可以看出,中间的这些不同颜色的交界处其实就是我们的decision boundaries,不同聚类与聚类之间的边界线。但是我们很多时候最好对于位于boundaries上面的每一个点仔细的考察一下,可能能够对于模型有更好的修正。

这里面的话,我们调节decision boundaries的时候,其实有很多种方法:1、改变我们的comparison function可以帮助我们调节我们的decision boundaries

2、我们可以改变判决的法则,之前我们只是从最接近的一个临接处进行分类;现在的话,我们需要结合已有分类中间的若干个点进行分类,然后进行一个majority vote从而得到对应的分类结果。

1.0.2.3 Distance Function

我们一般使用的comparison function对于一些经典的函数,我们总结称这些函数分别为:Distance function,我们常用的Distance 函数有以下,也就是我们常称的L-1,L-2距离。

当我们使用不同的distance function的时候,我们得到的结果也存在不同:

1.0.2.4 Hyper parameter 超参数

这里的话会引出来一个新的概念:超参数。超参数的意思其实并不是什么超级的意思,更多时候代表我们对于整个模型需要手动调节的参数。

这里的话,K代表的是我们选取的参考点的数目,可以是1,也可以是3,5等值。 Distance代表的是我们选择的Distance function,可以是L_1 Distance,也可以是L_2 Distance.

其实我们在整个神经网络的过程中,最重要的就是这个调参过程。怎么样获取一个更好的超参数呢?其实人们的方法也很蠢,就是不断的在数据集上面进行测试,不断的优化调节。

但其实在最后我们可以看到,平时我们正常的实践的时候,基本上还是不用这种Means或者说K-means方法的,其中有一个原因如下:

这个图片里我们可以看出来,我们的这里面3个图片有相同的L2距离。

同时的话,K-Means方法的运算量也是非常的巨大,其实不是很值得用做实际的应用。

1.0.3 线性分类器

Parametric Approach:

使用这个方法,通过把一幅图像经过我们设计好的一个系数矩阵操作之后,转换为10个类别标签。

其实总感觉这种方法和我们的稀疏字典有一些可以参考的关系,其实主要的工作量应该是在如何设计这个W系数矩阵。这里的话有一个实际的例子:

这一种方法的话,在最后其实和我们之前的聚类有一些类似的地方,同时也存在一些区别,不如说这里面每一个score的话,都有对应的得分。最后训练得到的每一个结果的话,都是对应的pattern。

上面这幅图仅仅是在CIFAR-10 数据集上训练得到的一个线性分类器,其实每个里面都能够看出来非常模糊的样子,特别是Car这个类别,特征算是比较明显的了。

线性分类器本质上做了哪些工作呢?其实他主要的作用就是通过建立几个线性分割线,把我们的线性空间进行了分割,从而实现一种分类的效果。

线性分类器这样子的话,看上去我们对于高维空间也能有不错的分割效果,那是不是我们只是用线性分类器就可以实现一切问题了呢?答案是否定的。线性分类器存在自身的失效的分类案例。

比如说下面的三个cases就是我们的线性分类器没有办法做到的问题——但是,其实第二个还是可以做到的,但是这里面的话首先就需要我们对于整个样本空间进行一个变换,把对应的部分转换到对应的样本空间之中,再使用线性的方法进行分割。

这里的话还有一个问题,我们学习到了一个系数矩阵,但是这个系数矩阵怎么样做能够使得我们可以很好的衡量这个分类器呢?我们的想法是:我们能不能通过构造一个函数,然后通过我们已知的分类之后的结果,对于正确分值的部分进行增加,错误分值的节点进行减小呢?

答案是可以的。这个时候就需要引出一个函数,来正确的表示我们的系数矩阵对于判断正确与否的影响关系。通过这个函数,我们能够知道往哪个方向来修正我们的系数矩阵。

2.0 Lecture 3 Loss function and optimaztion

2.0.1 Loss Function

Loss function:建立Loss function的目的是能够及时能够对我们的系数矩阵有一个修正;并且我们希望通过loss function来进行优化相关的parameter。

这里的话,我们建立了一个样本:${(x_i,y_i)}_{i=1}^N$,这里面的话$x_i$代表的是图片,$y_i$是标签。整个dataset的loss其实就是所有的样本的loss总和:
$$L = \frac{1}{N} \sum_i L_i(f(x_i,W),y_i)$$

这个是简单的一个总体loss的表达式。

2.0.2 Multiclass SVM loss

这里的话,$(x_i,y_i)$,其中$x_i$代表图片,$y_i$代表标签。这里的话有一个分数:$s = f(x_i,W)$,我们的SVM是有这样子的效果的:
$$L = begin{cases} 0, & text {if S_{y_i} bigger S_j+1 } \ s_j - S_{y_i}+1 , & text{otherwise}
end{cases}$$
$$L = \sum_{j \neq y_i} max(0,s_j - s_{y_j} +1)$$

举例:用一个例子演示公式是如何计算的。假设有3个分类,并且得到了分值s=[13,-7,11]。其中第一个类别是正确类别,即$y_i=0$。同时假设$\Delta$是10(后面会详细介绍该超参数)。上面的公式是将所有不正确分类$(j\not=y_i)$加起来,所以我们得到两个部分:

$ Li=max(0,-7-13+10)+max(0,11-13+10)$
可以看到第一个部分结果是0,这是因为$[-7-13+10]$得到的是负数,经过max(0,-)函数处理后得到0。这一对类别分数和标签的损失值是0,这是因为正确分类的得分13与错误分类的得分-7的差为20,高于边界值10。而SVM只关心差距至少要大于10,更大的差值还是算作损失值为0。第二个部分计算[11-13+10]得到8。虽然正确分类的得分比不正确分类的得分要高(13>11),但是比10的边界值还是小了,分差只有2,这就是为什么损失值等于8。简而言之,SVM的损失函数想要正确分类类别y_i的分数比不正确类别分数高,而且至少要高Delta。如果不满足这点,就开始计算损失值。

那么在这次的模型中,我们面对的是线性评分函数$(f(x_i,W)=Wx_i)$,所以我们可以将损失函数的公式稍微改写一下:

$L_i=\sum_{j\not=y_i}max(0,w^T_jx_i-w^T_{y_i}x_i+\Delta)$
其中$w_j$是权重$W$的第$j$行,被变形为列向量。然而,一旦开始考虑更复杂的评分函数f公式,这样做就不是必须的了。

在结束这一小节前,还必须提一下的属于是关于0的阀值:$max(0,-)$函数,它常被称为折叶损失(hinge loss)。有时候会听到人们使用平方折叶损失SVM(即L2-SVM),它使用的是$max(0,-)^2$,将更强烈(平方地而不是线性地)地惩罚过界的边界值。不使用平方是更标准的版本,但是在某些数据集中,平方折叶损失会工作得更好。可以通过交叉验证来决定到底使用哪个。

2.0.3 regularization 正则化

在上面的multiclass的损失函数中存在一个问题,这里的话假设我们有一个数据集和一个weight matrix W,这里的话可以正确的分类每一个数据(这里的话所有的边界都满足,对于所有的i都有$L_i = 0$),但是为题在于:这个W并不是唯一的,同时也有可能有很多相似的W可以正确的分类所有的数据。

换句话说,我们希望能向某些特定的权重W添加一些偏好,对其他权重则不添加,以此来消除模糊性。这一点是能够实现的,方法是向损失函数增加一个正则化惩罚(regularization penalty)$R(W)$部分。最常用的正则化惩罚是L2范式,L2范式通过对所有参数进行逐元素的平方惩罚来抑制大数值的权重:

$R(W)=\sum_k \sum_l W^2_{k,l}$
上面的表达式中,将W中所有元素平方后求和。注意正则化函数不是数据的函数,仅基于权重。包含正则化惩罚后,就能够给出完整的多类SVM损失函数了,它由两个部分组成:数据损失(data loss),即所有样例的的平均损失L_i,以及正则化损失(regularization loss)。完整公式如下所示:

$L= \underbrace{ \frac{1}{N}\sum_i L_i}_{data \ loss}+\underbrace{\lambda R(W)}_{regularization \ loss}$

将其展开完整公式是:

$L=\frac{1}{N}\sum_i\sum_{j\not=y_i}[max(0,f(x_i;W)_j-f(x_i;W)_{y_i}+\Delta)]+\lambda \sum_k \sum_l W^2_{k,l}$

其中,N是训练集的数据量。现在正则化惩罚添加到了损失函数里面,并用超参数lambda来计算其权重。该超参数无法简单确定,需要通过交叉验证来获取。

其中最好的性质就是对大数值权重进行惩罚,可以提升其泛化能力,因为这就意味着没有哪个维度能够独自对于整体分值有过大的影响。举个例子,假设输入向量$x=[1,1,1,1]$,两个权重向量$w_1=[1,0,0,0]$,$w_2=[0.25,0.25,0.25,0.25$。那么$w^T_1x=w^T_2=1$,两个权重向量都得到同样的内积,但是$w_1$的L2惩罚是1.0,而$w_2$的L2惩罚是0.25。因此,根据L2惩罚来看,$w_2$更好,因为它的正则化损失更小。从直观上来看,这是因为w_2的权重值更小且更分散。既然L2惩罚倾向于更小更分散的权重向量,这就会鼓励分类器最终将所有维度上的特征都用起来,而不是强烈依赖其中少数几个维度。在后面的课程中可以看到,这一效果将会提升分类器的泛化能力,并避免过拟合。

这里的话我们主要采用的Regularization方法分别有好几种,如下图所示:

2.0.4 SoftMax 函数(这一段从课程官方笔记整理)

Softmax分类器,它的损失函数与SVM的损失函数不同。对于学习过二元逻辑回归分类器的读者来说,Softmax分类器就可以理解为逻辑回归分类器面对多个分类的一般化归纳。SVM将输出$f(x_i,W)$作为每个分类的评分(因为无定标,所以难以直接解释)。与SVM不同,Softmax的输出(归一化的分类概率)更加直观,并且从概率上可以解释,这一点后文会讨论。在Softmax分类器中,函数映射$f(x_i;W)=Wx_i$保持不变,但将这些评分值视为每个分类的未归一化的对数概率,并且将折叶损失(hinge loss)替换为交叉熵损失(cross-entropy loss)。公式如下:

$$Li=-log(\frac{e^{f_{y_i}}}{\sum_je^{f_j}}) 或等价的 L_i=-f_{y_i}+log(\sum_je^{f_j})$$

在上式中,使用$f_j$来表示分类评分向量f中的第j个元素。和之前一样,整个数据集的损失值是数据集中所有样本数据的损失值L_i的均值与正则化损失R(W)之和。

其中函数$f_j(z)=\frac{e^{z_j}}{\sum_ke^{z_k}}$被称作softmax 函数:其输入值是一个向量,向量中元素为任意实数的评分值(z中的),函数对其进行压缩,输出一个向量,其中每个元素值在0到1之间,且所有元素之和为1。

信息理论视角:在“真实”分布p和估计分布q之间的交叉熵定义如下:

$$H(p,q)=-\sum_xp(x) logq(x)$$
因此,Softmax分类器所做的就是最小化在估计分类概率(就是上面的$e^{f_{y_i}}/\sum_je^{f_j})$和“真实”分布之间的交叉熵,在这个解释中,“真实”分布就是所有概率密度都分布在正确的类别上(比如:$p=[0,...1,...,0]$中在$y_i$的位置就有一个单独的1)。还有,既然交叉熵可以写成熵和相对熵(Kullback-Leibler divergence)$H(p,q)=H(p)+D_{KL}(p||q)$,并且delta函数p的熵是0,那么就能等价的看做是对两个分布之间的相对熵做最小化操作。换句话说,交叉熵损失函数“想要”预测分布的所有概率密度都在正确分类上。

译者注:Kullback-Leibler差异(Kullback-Leibler Divergence)也叫做相对熵(Relative Entropy),它衡量的是相同事件空间里的两个概率分布的差异情况。

概率论解释:先看下面的公式:

$$P(y_i|x_i,W)=\frac{e^{f_{y_i}}}{\sum_je^{f_j}}$$
可以解释为是给定图像数据$x_i$,以W为参数,分配给正确分类标签$y_i$的归一化概率。为了理解这点,请回忆一下Softmax分类器将输出向量f中的评分值解释为没有归一化的对数概率。那么以这些数值做指数函数的幂就得到了没有归一化的概率,而除法操作则对数据进行了归一化处理,使得这些概率的和为1。从概率论的角度来理解,我们就是在最小化正确分类的负对数概率,这可以看做是在进行最大似然估计(MLE)。该解释的另一个好处是,损失函数中的正则化部分R(W)可以被看做是权重矩阵W的高斯先验,这里进行的是最大后验估计(MAP)而不是最大似然估计。提及这些解释只是为了让读者形成直观的印象,具体细节就超过本课程范围了。

实操事项:数值稳定。编程实现softmax函数计算的时候,中间项$e^{f_{y_i}}$和$\sum_j e^{f_j}$因为存在指数函数,所以数值可能非常大。除以大数值可能导致数值计算的不稳定,所以学会使用归一化技巧非常重要。如果在分式的分子和分母都乘以一个常数C,并把它变换到求和之中,就能得到一个从数学上等价的公式:

$$\frac{e^{f_{y_i}}}{\sum_je^{f_j}}=\frac{Ce^{f_{y_i}}}{C\sum_je^{f_j}}=\frac{e^{f_{y_i}+logC}}{\sum_je^{f_j+logC}}$$
C的值可自由选择,不会影响计算结果,通过使用这个技巧可以提高计算中的数值稳定性。通常将C设为$logC=-max_jf_j$。该技巧简单地说,就是应该将向量f中的数值进行平移,使得最大值为0。代码实现如下:

f = np.array([123, 456, 789]) # 例子中有3个分类,每个评分的数值都很大
p = np.exp(f) / np.sum(np.exp(f)) # 不妙:数值问题,可能导致数值爆炸

# 那么将f中的值平移到最大值为0:
f -= np.max(f) # f becomes [-666, -333, 0]
p = np.exp(f) / np.sum(np.exp(f)) # 现在OK了,将给出正确结果


2.0.5 Softmax 和 SVM的比较

其实可以看得出,我们使用softmax和svm的时候,都是同时对于我们的得到的score函数进行一个判决。

不同的是他们的判决方法是不同的。SVM分类器将它们看做是分类评分,它的损失函数鼓励正确的分类的分值比其他分类的分值高出至少一个边界值。Softmax分类器将这些数值看做是每个分类没有归一化的对数概率,鼓励正确分类的归一化的对数概率变高,其余的变低。(其实softmax更加的直观一些)

2.0.6 优化问题

一般来说的话,我们对于图像数据$x_i$,我们如果对于参数集$W$做出来的分类预测和我们的真实情况一致的话,那么我们的loss $L$就很小。

这里面的话,其实我们就是希望通过我们的优化方法能够实现损失函数最小化参数$W$的过程。

这里的话,整个课程里面举的例子是:人们沿着一个路线下山,如果没有地图,我们怎么样最快的下山呢?最好的办法,沿着最陡峭的地方下山。最终我们如果到达了山谷,那么我们在山谷这一点的斜率可以近似的看作是0.

这里的话,根据Justin整理的课程笔记的话,由于我们是进行神经网络的深度学习的,我们一般的损失函数都是定义在高纬度的空间中间的,这里我们是仅仅使用CIFAR-10数据集的话,我们的线性分类器的权重矩阵的大小就是$[10*3073]$,总共有30730个参数。这个时候的话,我们如果想要把这个损失函数可视化就非常的苦难了。但是这个时候,我们如果在某几个维度上面对高维空间进行了切片处理,我们就可以近似的知道这个时候的导数变化情况。

这里的话,我们想要让我们的损失函数达到极小值,那我们应该怎么办呢?这时候有三个备选方法:

方法一:随机搜索;在随机搜索的时候,我们随机的尝试很多不同的权重,然后根据不同的权重对应的损失函数,进而比较哪一个最好。这种办法的话成功的准确率是很低的。

方法二:沿斜率下降;在我们的一维空间中,我们的函数的导数定义如下:$$\frac{df(x)}{dx} = \lim_{h \to 0}\frac{f(x+h)-f(x)}{h}$$

在多维的空间中,我们的导数定义的话没有那么复杂,仅仅是使用我们在各个方向上的梯度就可以解决。这里的话,我们在每一个方向上面的斜率的话其实就是这个点上面导数和方向的点乘积,某一个方向上面如果斜率最大那么就可以称之为是negative gradient。

这种方法的话其实就很像是我们的迭代方法,如果我们不达到局部最优,我们就跳不出我们的迭代过程。

这种方法其实可能也比较直观,但是因为使用了迭代,运算的复杂度其实是比较大的。

方法三:这里的话,其实和上课的课件是存在区别的,这里的话我们按照justin整理的笔记为主,这种方法我们称之为随机本地搜索。

我们上面的方法的话,其实可以看作是我们每走一步都随机的选择几个方向,如果这个方向是朝着山下的那么我们就下降一步。我们新的方法的话,我们从一个完全随机的$W$开始,在之后每一次我们随机的产生一个小的偏差(将来报道出现了偏差,我也有责任的)$\delta W$,这个时候只有我们的$W + \delta W$这个损失降低了,我们才会更新我们的模型。

===上面的话,由于是根据PPT和Justin的笔记一起进行写的,所以可能逻辑上不是很清晰,但是内容都覆盖到了===

2.0.7 梯度的计算

我们一般的话,其实在计算机实现计算梯度的方法有两种:

第一种办法:数值梯度法,这种方法其实就是我们一开始学习导数时候的数值方法,这种方法我们自己用起来方便,同时实现也就简单;

第二种方法:分析梯度法:其实就是数学方法人工计算梯度表达式,这里面的话计算迅速(还不是因为我们人工已经搞定了),计算结果精确,但是在实现的时候容易出错,同时需要使用微分。

这里的恶化,可以参考一下给出来的python代码,看一看numerical gradient:下面的代码中,输入是函数f和向量x,计算返回f在x的梯度

'''python

def eval_numerical_gradient(f,x):

fx = f(x)
grad = np.zeros(x.shape)
h = 0.000001

it = np.nditer(x,flags = ['multi_index'],op_flags = ['readwrite'])
while not ot.finished:

ix = it.multi_index
old_value = x[ix]
x[ix] = old_value + h
fxh = f(x)
x[ix] = old_value

grad[ix] = (fxh - fx) /h
it.iternext()

return grad

'''


如果觉得我的文章对你有用,请随意赞赏

你可能感兴趣的

载入中...