diff --git "a/ch01_\346\225\260\345\255\246\345\237\272\347\241\200/\347\254\254\344\270\200\347\253\240_\346\225\260\345\255\246\345\237\272\347\241\200.md" "b/ch01_\346\225\260\345\255\246\345\237\272\347\241\200/\347\254\254\344\270\200\347\253\240_\346\225\260\345\255\246\345\237\272\347\241\200.md" index 27f26799..932fbf47 100644 --- "a/ch01_\346\225\260\345\255\246\345\237\272\347\241\200/\347\254\254\344\270\200\347\253\240_\346\225\260\345\255\246\345\237\272\347\241\200.md" +++ "b/ch01_\346\225\260\345\255\246\345\237\272\347\241\200/\347\254\254\344\270\200\347\253\240_\346\225\260\345\255\246\345\237\272\347\241\200.md" @@ -2,16 +2,6 @@ # 第一章 数学基础 -> Markdown Revision 1; --update 2018/10/30 13:00 - -> Date: 2018/10/25 -- 2018/10/30 -- 2018/11/01 - -> Editor: 谈继勇 &乔成磊-同济大学 & 哈工大博士生-袁笛 - -> Contact: scutjy2015@163.com & qchl0318@163.com & dyuanhit@gmail.com - - - ## 1.1 标量、向量、矩阵、张量之间的联系 **标量(scalar)** ​一个标量表示一个单独的数,它不同于线性代数中研究的其他大部分对象(通常是多个数的数组)。我们用斜体表示标量。标量通常被赋予小写的变量名称。 @@ -69,15 +59,15 @@ $$ \Vert\vec{x}\Vert_{+\infty}=\max{|{x_i}|} $$ -- 向量的p范数:向量元素绝对值的p次方和的1/p次幂。 - +- 向量的p范数: + $$ L_p=\Vert\vec{x}\Vert_p=\sqrt[p]{\sum_{i=1}^{N}|{x_i}|^p} $$ **矩阵的范数** -​定义一个矩阵$A=[-1, 2, -3; 4, -6, 6]$。 任意矩阵定义为:$A_{m\times n}$,其元素为 $a_{ij}$。 +定义一个矩阵$A=[-1, 2, -3; 4, -6, 6]$。 任意矩阵定义为:$A_{m\times n}$,其元素为 $a_{ij}$。 矩阵的范数定义为 @@ -85,16 +75,16 @@ $$ \Vert{A}\Vert_p :=\sup_{x\neq 0}\frac{\Vert{Ax}\Vert_p}{\Vert{x}\Vert_p} $$ -​当向量取不同范数时, 相应得到了不同的矩阵范数。 +当向量取不同范数时, 相应得到了不同的矩阵范数。 - **矩阵的1范数(列范数)**:矩阵的每一列上的元素绝对值先求和,再从中取个最大的,(列和最大),上述矩阵$A$的1范数先得到$[5,8,9]$,再取最大的最终结果就是:9。 $$ -\Vert A\Vert_1=\max_{1\le j\le n}\sum_{i=1}^m|{a_{ij}}| +\Vert A\Vert_1=\max_{1\le j\le}\sum_{i=1}^m|{a_{ij}}| $$ - **矩阵的2范数**:矩阵$A^TA$的最大特征值开平方根,上述矩阵$A$的2范数得到的最终结果是:10.0623。 - + $$ \Vert A\Vert_2=\sqrt{\lambda_{max}(A^T A)} $$ @@ -110,7 +100,7 @@ $$ - **矩阵的L0范数**:矩阵的非0元素的个数,通常用它来表示稀疏,L0范数越小0元素越多,也就越稀疏,上述矩阵$A$最终结果就是:6。 - **矩阵的L1范数**:矩阵中的每个元素绝对值之和,它是L0范数的最优凸近似,因此它也可以表示稀疏,上述矩阵$A$最终结果就是:22。 -- **矩阵的F范数**:矩阵的各个元素平方之和再开平方根,它通常也叫做矩阵的L2范数,它的优点在它是一个凸函数,可以求导求解,易于计算,上述矩阵A最终结果就是:10.0995。 +- **矩阵的F范数**:矩阵的各个元素平方之和再开平方根,它通常也叫做矩阵的L2范数,它的有点在它是一个凸函数,可以求导求解,易于计算,上述矩阵A最终结果就是:10.0995。 $$ \Vert A\Vert_F=\sqrt{(\sum_{i=1}^m\sum_{j=1}^n{| a_{ij}|}^2)} @@ -135,7 +125,7 @@ $$ ## 1.6 导数偏导计算 **导数定义**: -​导数代表了在自变量变化趋于无穷小的时候,函数值的变化与自变量的变化的比值。几何意义是这个点的切线。物理意义是该时刻的(瞬时)变化率。 +导数代表了在自变量变化趋于无穷小的时候,函数值的变化与自变量的变化的比值。几何意义是这个点的切线。物理意义是该时刻的(瞬时)变化率。 ​ *注意*:在一元函数中,只有一个自变量变动,也就是说只存在一个方向的变化率,这也就是为什么一元函数没有偏导数的原因。在物理学中有平均速度和瞬时速度之说。平均速度有 @@ -144,49 +134,49 @@ $$ v=\frac{s}{t} $$ -​其中$v$表示平均速度,$s$表示路程,$t$表示时间。这个公式可以改写为 +其中$v$表示平均速度,$s$表示路程,$t$表示时间。这个公式可以改写为 $$ \bar{v}=\frac{\Delta s}{\Delta t}=\frac{s(t_0+\Delta t)-s(t_0)}{\Delta t} $$ -​其中$\Delta s$表示两点之间的距离,而$\Delta t$表示走过这段距离需要花费的时间。当$\Delta t$趋向于0($\Delta t \to 0$)时,也就是时间变得很短时,平均速度也就变成了在$t_0$时刻的瞬时速度,表示成如下形式: +其中$\Delta s$表示两点之间的距离,而$\Delta t$表示走过这段距离需要花费的时间。当$\Delta t$趋向于0($\Delta t \to 0$)时,也就是时间变得很短时,平均速度也就变成了在$t_0$时刻的瞬时速度,表示成如下形式: $$ v(t_0)=\lim_{\Delta t \to 0}{\bar{v}}=\lim_{\Delta t \to 0}{\frac{\Delta s}{\Delta t}}=\lim_{\Delta t \to 0}{\frac{s(t_0+\Delta t)-s(t_0)}{\Delta t}} $$ -​实际上,上式表示的是路程$s$关于时间$t$的函数在$t=t_0$处的导数。一般的,这样定义导数:如果平均变化率的极限存在,即有 +实际上,上式表示的是路程$s$关于时间$t$的函数在$t=t_0$处的导数。一般的,这样定义导数:如果平均变化率的极限存在,即有 $$ \lim_{\Delta x \to 0}{\frac{\Delta y}{\Delta x}}=\lim_{\Delta x \to 0}{\frac{f(x_0+\Delta x)-f(x_0)}{\Delta x}} $$ -​则称此极限为函数 $y=f(x)$ 在点 $x_0$ 处的导数。记作 $f'(x_0)$ 或 $y'\vert_{x=x_0}$ 或 $\frac{dy}{dx}\vert_{x=x_0}$ 或 $\frac{df(x)}{dx}\vert_{x=x_0}$。 +则称此极限为函数 $y=f(x)$ 在点 $x_0$ 处的导数。记作 $f'(x_0)$ 或 $y'\vert_{x=x_0}$ 或 $\frac{dy}{dx}\vert_{x=x_0}$ 或 $\frac{df(x)}{dx}\vert_{x=x_0}$。 -​通俗地说,导数就是曲线在某一点切线的斜率。 +通俗地说,导数就是曲线在某一点切线的斜率。 **偏导数**: -​既然谈到偏导数,那就至少涉及到两个自变量。以两个自变量为例,z=f(x,y),从导数到偏导数,也就是从曲线来到了曲面。曲线上的一点,其切线只有一条。但是曲面上的一点,切线有无数条。而偏导数就是指多元函数沿着坐标轴的变化率。 +既然谈到偏导数,那就至少涉及到两个自变量。以两个自变量为例,z=f(x,y),从导数到偏导数,也就是从曲线来到了曲面。曲线上的一点,其切线只有一条。但是曲面上的一点,切线有无数条。而偏导数就是指多元函数沿着坐标轴的变化率。 ​ *注意*:直观地说,偏导数也就是函数在某一点上沿坐标轴正方向的的变化率。 -​设函数$z=f(x,y)$在点$(x_0,y_0)$的领域内有定义,当$y=y_0$时,$z$可以看作关于$x$的一元函数$f(x,y_0)$,若该一元函数在$x=x_0$处可导,即有 +设函数$z=f(x,y)$在点$(x_0,y_0)$的领域内有定义,当$y=y_0$时,$z$可以看作关于$x$的一元函数$f(x,y_0)$,若该一元函数在$x=x_0$处可导,即有 $$ \lim_{\Delta x \to 0}{\frac{f(x_0+\Delta x,y_0)-f(x_0,y_0)}{\Delta x}}=A $$ -​函数的极限$A$存在。那么称$A$为函数$z=f(x,y)$在点$(x_0,y_0)$处关于自变量$x$的偏导数,记作$f_x(x_0,y_0)$或$\frac{\partial z}{\partial x}\vert_{y=y_0}^{x=x_0}$或$\frac{\partial f}{\partial x}\vert_{y=y_0}^{x=x_0}$或$z_x\vert_{y=y_0}^{x=x_0}$。 +函数的极限$A$存在。那么称$A$为函数$z=f(x,y)$在点$(x_0,y_0)$处关于自变量$x$的偏导数,记作$f_x(x_0,y_0)$或$\frac{\partial z}{\partial x}\vert_{y=y_0}^{x=x_0}$或$\frac{\partial f}{\partial x}\vert_{y=y_0}^{x=x_0}$或$z_x\vert_{y=y_0}^{x=x_0}$。 -​偏导数在求解时可以将另外一个变量看做常数,利用普通的求导方式求解,比如$z=3x^2+xy$关于$x$的偏导数就为$z_x=6x+y$,这个时候$y$相当于$x$的系数。 +偏导数在求解时可以将另外一个变量看做常数,利用普通的求导方式求解,比如$z=3x^2+xy$关于$x$的偏导数就为$z_x=6x+y$,这个时候$y$相当于$x$的系数。 -​某点$(x_0,y_0)$处的偏导数的几何意义为曲面$z=f(x,y)$与面$x=x_0$或面$y=y_0$交线在$y=y_0$或$x=x_0$处切线的斜率。 +某点$(x_0,y_0)$处的偏导数的几何意义为曲面$z=f(x,y)$与面$x=x_0$或面$y=y_0$交线在$y=y_0$或$x=x_0$处切线的斜率。 ## 1.7 导数和偏导数有什么区别? -​导数和偏导没有本质区别,如果极限存在,都是当自变量的变化量趋于0时,函数值的变化量与自变量变化量比值的极限。 +导数和偏导没有本质区别,如果极限存在,都是当自变量的变化量趋于0时,函数值的变化量与自变量变化量比值的极限。 > - 一元函数,一个$y$对应一个$x$,导数只有一个。 > - 二元函数,一个$z$对应一个$x$和一个$y$,有两个导数:一个是$z$对$x$的导数,一个是$z$对$y$的导数,称之为偏导。 @@ -204,15 +194,15 @@ A\nu = \lambda \nu $$ $\lambda$为特征向量$\vec{v}$对应的特征值。特征值分解是将一个矩阵分解为如下形式: -​ + $$ -A=Q\Sigma Q^{-1} +A=Q\sum Q^{-1} $$ -其中,$Q$是这个矩阵$A$的特征向量组成的矩阵,$\Sigma$是一个对角矩阵,每一个对角线元素就是一个特征值,里面的特征值是由大到小排列的,这些特征值所对应的特征向量就是描述这个矩阵变化方向(从主要的变化到次要的变化排列)。也就是说矩阵$A$的信息可以由其特征值和特征向量表示。 +其中,$Q$是这个矩阵$A$的特征向量组成的矩阵,$\sum$是一个对角矩阵,每一个对角线元素就是一个特征值,里面的特征值是由大到小排列的,这些特征值所对应的特征向量就是描述这个矩阵变化方向(从主要的变化到次要的变化排列)。也就是说矩阵$A$的信息可以由其特征值和特征向量表示。 ## 1.9 奇异值与特征值有什么关系? -​那么奇异值和特征值是怎么对应起来的呢?我们将一个矩阵$A$的转置乘以$A$,并对$AA^T$求特征值,则有下面的形式: +那么奇异值和特征值是怎么对应起来的呢?我们将一个矩阵$A$的转置乘以$A$,并对$AA^T$求特征值,则有下面的形式: $$ (A^TA)V = \lambda V @@ -225,16 +215,16 @@ $$ $$ 这里的$\sigma$就是奇异值,$u$就是上面说的左奇异向量。【证明那个哥们也没给】 -​奇异值$\sigma$跟特征值类似,在矩阵$\Sigma$中也是从大到小排列,而且$\sigma$的减少特别的快,在很多情况下,前10%甚至1%的奇异值的和就占了全部的奇异值之和的99%以上了。也就是说,我们也可以用前$r$($r$远小于$m、n$)个的奇异值来近似描述矩阵,即部分奇异值分解: +​奇异值$\sigma$跟特征值类似,在矩阵$\sum$中也是从大到小排列,而且$\sigma$的减少特别的快,在很多情况下,前10%甚至1%的奇异值的和就占了全部的奇异值之和的99%以上了。也就是说,我们也可以用前$r$($r$远小于$m、n$)个的奇异值来近似描述矩阵,即部分奇异值分解: $$ -A_{m\times n}\approx U_{m \times r}\Sigma_{r\times r}V_{r \times n}^T +A_{m\times n}\approx U_{m \times r}\sum_{r\times r}V_{r \times n}^T $$ 右边的三个矩阵相乘的结果将会是一个接近于$A$的矩阵,在这儿,$r$越接近于$n$,则相乘的结果越接近于$A$。 ## 1.10 机器学习为什么要使用概率? -​事件的概率是衡量该事件发生的可能性的量度。虽然在一次随机试验中某个事件的发生是带有偶然性的,但那些可在相同条件下大量重复的随机试验却往往呈现出明显的数量规律。 +事件的概率是衡量该事件发生的可能性的量度。虽然在一次随机试验中某个事件的发生是带有偶然性的,但那些可在相同条件下大量重复的随机试验却往往呈现出明显的数量规律。 ​机器学习除了处理不确定量,也需处理随机量。不确定性和随机性可能来自多个方面,使用概率论来量化不确定性。 ​概率论在机器学习中扮演着一个核心角色,因为机器学习算法的设计通常依赖于对数据的概率假设。 @@ -243,7 +233,7 @@ $$ ## 1.11 变量与随机变量有什么区别? **随机变量**(random variable) -​表示随机现象(在一定条件下,并不总是出现相同结果的现象称为随机现象)中各种结果的实值函数(一切可能的样本点)。例如某一时间内公共汽车站等车乘客人数,电话交换台在一定时间内收到的呼叫次数等,都是随机变量的实例。 +表示随机现象(在一定条件下,并不总是出现相同结果的现象称为随机现象)中各种结果的实值函数(一切可能的样本点)。例如某一时间内公共汽车站等车乘客人数,电话交换台在一定时间内收到的呼叫次数等,都是随机变量的实例。 ​随机变量与模糊变量的不确定性的本质差别在于,后者的测定结果仍具有不确定性,即模糊性。 **变量与随机变量的区别:** @@ -253,33 +243,161 @@ $$ > ​ 当变量$x$值为100的概率为1的话,那么$x=100$就是确定了的,不会再有变化,除非有进一步运算. > ​ 当变量$x$的值为100的概率不为1,比如为50的概率是0.5,为100的概率是0.5,那么这个变量就是会随不同条件而变化的,是随机变量,取到50或者100的概率都是0.5,即50%。 -## 1.12 常见概率分布 -(https://wenku.baidu.com/view/6418b0206d85ec3a87c24028915f804d2b168707) -![常见概率分布](./img/ch1/prob_distribution_1.png) -![常见概率分布](./img/ch1/prob_distribution_2.png) -![常见概率分布](./img/ch1/prob_distribution_3.png) -![常见概率分布](./img/ch1/prob_distribution_4.png) -![常见概率分布](./img/ch1/prob_distribution_5.png) -![常见概率分布](./img/ch1/prob_distribution_6.png) -![常见概率分布](./img/ch1/prob_distribution_7.png) +## 1.12 随机变量与概率分布的联系? + +一个随机变量仅仅表示一个可能取得的状态,还必须给定与之相伴的概率分布来制定每个状态的可能性。用来描述随机变量或一簇随机变量的每一个可能的状态的可能性大小的方法,就是 **概率分布(probability distribution)**. + +随机变量可以分为离散型随机变量和连续型随机变量。 + +相应的描述其概率分布的函数是 + +概率质量函数(Probability Mass Function, PMF):描述离散型随机变量的概率分布,通常用大写字母 $P$表示。 + +概率密度函数(Probability Density Function, PDF):描述连续型随机变量的概率分布,通常用小写字母$p$表示。 + +### 1.12.1 离散型随机变量和概率质量函数 + +PMF 将随机变量能够取得的每个状态映射到随机变量取得该状态的概率。 + +- 一般而言,$P(x)$ 表示时$X=x​$的概率. +- 有时候为了防止混淆,要明确写出随机变量的名称$P(​$x$=x)​$ +- 有时候需要先定义一个随机变量,然后制定它遵循的概率分布x服从$P($x​$)​$ + +PMF 可以同时作用于多个随机变量,即联合概率分布(joint probability distribution) $P(X=x,Y=y)​$*表示 $X=x​$和 同$Y=y​$发生的概率,也可以简写成 $P(x,y)​$. + +如果一个函数$P​$是随机变量 $X​$ 的 PMF, 那么它必须满足如下三个条件 + +- $P​$的定义域必须是的所有可能状态的集合 +- $∀x∈​$x, $0 \leq P(x) \leq 1 ​$. +- $∑_{x∈X} P(x)=1$. 我们把这一条性质称之为 归一化的(normalized) + +### 1.12.2 连续型随机变量和概率密度函数 + +如果一个函数$p​$是x的PDF,那么它必须满足如下几个条件 + +- $p$的定义域必须是 xx 的所有可能状态的集合。 +- $∀x∈X,p(x)≥0$. 注意,我们并不要求$ p(x)≤1$,因为此处 $p(x)$不是表示的对应此状态具体的概率,而是概率的一个相对大小(密度)。具体的概率,需要积分去求。 +- $∫p(x)dx=1$, 积分下来,总和还是1,概率之和还是1. + +注:PDF$p(x)$并没有直接对特定的状态给出概率,给出的是密度,相对的,它给出了落在面积为 $δx$的无线小的区域内的概率为$ p(x)δx$. 由此,我们无法求得具体某个状态的概率,我们可以求得的是 某个状态 $x$ 落在 某个区间$[a,b]$内的概率为$ \int_{a}^{b}p(x)dx$. + +## 1.13 常见概率分布 + +### 1.13.1 Bernoulli分布 + +**Bernoulli分布**是单个二值随机变量分布, 单参数$\phi​$∈[0,1]控制,$\phi​$给出随机变量等于1的概率. 主要性质有: +$$ +\begin{align*} +P(x=1) &= \phi \\ +P(x=0) &= 1-\phi \\ +P(x=x) &= \phi^x(1-\phi)^{1-x} \\ +\end{align*} +$$ +其期望和方差为: +$$ +\begin{align*} +E_x[x] &= \phi \\ +Var_x(x) &= \phi{(1-\phi)} +\end{align*} +$$ +**Multinoulli分布**也叫**范畴分布**, 是单个*k*k值随机分布,经常用来表示**对象分类的分布**. 其中$k​$是有限值.Multinoulli分布由向量$\vec{p}\in[0,1]^{k-1}​$参数化,每个分量$p_i​$表示第$i​$个状态的概率, 且$p_k=1-1^Tp​$. + +**适用范围**: **伯努利分布**适合对**离散型**随机变量建模. + +### 1.13.2 高斯分布 + +高斯也叫正态分布(Normal Distribution), 概率度函数如下: +$$ +N(x;\mu,\sigma^2) = \sqrt{\frac{1}{2\pi\sigma^2}}exp\left ( -\frac{1}{2\sigma^2}(x-\mu)^2 \right ) +$$ +其中, $\mu​$和$\sigma​$分别是均值和方差, 中心峰值x坐标由$\mu​$给出, 峰的宽度受$\sigma​$控制, 最大点在$x=\mu​$处取得, 拐点为$x=\mu\pm\sigma​$ + +正态分布中,±1$\sigma$、±2$\sigma$、±3$\sigma$下的概率分别是68.3%、95.5%、99.73%,这3个数最好记住。 + +此外, 令$\mu=0,\sigma=1​$高斯分布即简化为标准正态分布: +$$ +N(x;\mu,\sigma^2) = \sqrt{\frac{1}{2\pi}}exp\left ( -\frac{1}{2}x^2 \right ) +$$ +对概率密度函数高效求值: +$$ +N(x;\mu,\beta^{-1})=\sqrt{\frac{\beta}{2\pi}}exp\left(-\frac{1}{2}\beta(x-\mu)^2\right) +$$ + + +其中,$\beta=\frac{1}{\sigma^2}$通过参数$\beta∈(0,\infty)​$来控制分布精度。 + +### 1.13.3 何时采用正态分布? + +问: 何时采用正态分布? +答: 缺乏实数上分布的先验知识, 不知选择何种形式时, 默认选择正态分布总是不会错的, 理由如下: + +1. 中心极限定理告诉我们, 很多独立随机变量均近似服从正态分布, 现实中很多复杂系统都可以被建模成正态分布的噪声, 即使该系统可以被结构化分解. +2. 正态分布是具有相同方差的所有概率分布中, 不确定性最大的分布, 换句话说, 正态分布是对模型加入先验知识最少的分布. + +正态分布的推广: +正态分布可以推广到$R^n$空间, 此时称为**多位正态分布**, 其参数是一个正定对称矩阵$\sum$: +$$ +N(x;\vec\mu,\sum)=\sqrt{\frac{1}{2\pi^ndet(\sum)}}exp\left(-\frac{1}{2}(\vec{x}-\vec{\mu})^T\sum^-1(\vec{x}-\vec{\mu})\right) +$$ +对多为正态分布概率密度高效求值: +$$ +N(x;\vec{\mu},\vec\beta^{-1}) = \sqrt{det(\vec\beta)}{(2\pi)^n}exp\left(-\frac{1}{2}(\vec{x}-\vec\mu)^T\beta(\vec{x}-\vec\mu)\right) +$$ +此处,$\vec\beta$是一个精度矩阵。 + +### 1.13.4 指数分布 + +深度学习中, 指数分布用来描述在$x=0$点出取得边界点的分布, 指数分布定义如下: +$$ +p(x;\lambda)=\lambda1_{x\geq 0}exp(-\lambda{x}) +$$ +指数分布用指示函数$I_{x>=0}$来使$x$取负值时的概率为零。 + +### 1.13.5 Laplace 分布 + +一个联系紧密的概率分布是 Laplace 分布(Laplace distribution),它允许我们在任意一点 $\mu$处设置概率质量的峰值 +$$ +Laplace(x;\mu;\gamma)=\frac{1}{2\gamma}exp\left(-\frac{|x-\mu|}{\gamma}\right) +$$ + +### 1.13.6 Dirac分布和经验分布 + +Dirac分布可保证概率分布中所有质量都集中在一个点上. Diract分布的狄拉克$\delta​$函数(也称为**单位脉冲函数**)定义如下: +$$ +p(x)=\delta(x-\mu), x\neq \mu +$$ + +$$ +\int_{a}^{b}\delta(x-\mu)dx = 1, a < \mu < b +$$ + +Dirac 分布经常作为 经验分布(empirical distribution)的一个组成部分出现 +$$ +\hat{p}(\vec{x})=\frac{1}{m}\sum_{i=1}^{m}\delta(\vec{x}-{\vec{x}}^{(i)}) +$$ +, 其中, m个点$x^{1},...,x^{m}$是给定的数据集, **经验分布**将概率密度$\frac{1}{m}​$赋给了这些点. + +当我们在训练集上训练模型时, 可以认为从这个训练集上得到的经验分布指明了**采样来源**. + +**适用范围**: 狄拉克δ函数适合对**连续型**随机变量的经验分布. -## 1.13 举例理解条件概率 -​条件概率公式如下: +## 1.14 举例理解条件概率 +条件概率公式如下: $$ P(A/B) = P(A\cap B) / P(B) $$ -​说明:在同一个样本空间$\Omega$中的事件或者子集$A$与$B$,如果随机从$\Omega$中选出的一个元素属于$B$,那么下一个随机选择的元素属于$A$ 的概率就定义为在$B$的前提下$A$的条件概率。 +说明:在同一个样本空间$\Omega$中的事件或者子集$A$与$B$,如果随机从$\Omega$中选出的一个元素属于$B$,那么下一个随机选择的元素属于$A$ 的概率就定义为在$B$的前提下$A$的条件概率。 ![条件概率](./img/ch1/conditional_probability.jpg) -​根据文氏图,可以很清楚地看到在事件B发生的情况下,事件A发生的概率就是$P(A\bigcap B)$除以$P(B)$。 +根据文氏图,可以很清楚地看到在事件B发生的情况下,事件A发生的概率就是$P(A\bigcap B)$除以$P(B)$。 ​举例:一对夫妻有两个小孩,已知其中一个是女孩,则另一个是女孩子的概率是多少?(面试、笔试都碰到过) ​**穷举法**:已知其中一个是女孩,那么样本空间为男女,女女,女男,则另外一个仍然是女生的概率就是1/3。 ​**条件概率法**:$P(女|女)=P(女女)/P(女)$,夫妻有两个小孩,那么它的样本空间为女女,男女,女男,男男,则$P(女女)$为1/4,$P(女)= 1-P(男男)=3/4$,所以最后$1/3$。 这里大家可能会误解,男女和女男是同一种情况,但实际上类似姐弟和兄妹是不同情况。 -## 1.14 联合概率与边缘概率联系区别? +## 1.15 联合概率与边缘概率联系区别? **区别:** ​联合概率:联合概率指类似于$P(X=a,Y=b)$这样,包含多个条件,且所有条件同时成立的概率。联合概率是指在多元的概率分布中多个随机变量分别满足各自条件的概率。 ​边缘概率:边缘概率是某个事件发生的概率,而与其它事件无关。边缘概率指类似于$P(X=a)$,$P(Y=b)$这样,仅与单个随机变量有关的概率。 @@ -287,30 +405,30 @@ $$ **联系:** ​联合分布可求边缘分布,但若只知道边缘分布,无法求得联合分布。 -## 1.15 条件概率的链式法则 -​由条件概率的定义,可直接得出下面的乘法公式: +## 1.16 条件概率的链式法则 +由条件概率的定义,可直接得出下面的乘法公式: ​乘法公式 设$A, B$是两个事件,并且$P(A) > 0$, 则有 $$ P(AB) = P(B|A)P(A) $$ -​推广 +推广 $$ P(ABC)=P(C|AB)P(B|A)P(A) $$ -​一般地,用归纳法可证:若$P(A_1A_2...A_n)>0$,则有 +一般地,用归纳法可证:若$P(A_1A_2...A_n)>0$,则有 $$ P(A_1A_2...A_n)=P(A_n|A_1A_2...A_{n-1})P(A_{n-1}|A_1A_2...A_{n-2})...P(A_2|A_1)P(A_1) =P(A_1)\prod_{i=2}^{n}P(A_i|A_1A_2...A_{i-1}) $$ -​任何多维随机变量联合概率分布,都可以分解成只有一个变量的条件概率相乘形式。 +任何多维随机变量联合概率分布,都可以分解成只有一个变量的条件概率相乘形式。 -## 1.16 独立性和条件独立性 +## 1.17 独立性和条件独立性 **独立性** ​两个随机变量$x$和$y$,概率分布表示成两个因子乘积形式,一个因子只包含$x$,另一个因子只包含$y$,两个随机变量相互独立(independent)。 ​条件有时为不独立的事件之间带来独立,有时也会把本来独立的事件,因为此条件的存在,而失去独立性。 @@ -320,7 +438,7 @@ $$ P(X,Y|Z) \not = P(X|Z)P(Y|Z) $$ -​事件独立时,联合概率等于概率的乘积。这是一个非常好的数学性质,然而不幸的是,无条件的独立是十分稀少的,因为大部分情况下,事件之间都是互相影响的。 +事件独立时,联合概率等于概率的乘积。这是一个非常好的数学性质,然而不幸的是,无条件的独立是十分稀少的,因为大部分情况下,事件之间都是互相影响的。 **条件独立性** ​给定$Z$的情况下,$X$和$Y$条件独立,当且仅当 @@ -329,7 +447,7 @@ $$ X\bot Y|Z \iff P(X,Y|Z) = P(X|Z)P(Y|Z) $$ -​$X$和$Y$的关系依赖于$Z$,而不是直接产生。 +$X$和$Y$的关系依赖于$Z$,而不是直接产生。 >**举例**定义如下事件: >$X$:明天下雨; @@ -337,11 +455,11 @@ $$ >$Z$:今天是否下雨; >$Z$事件的成立,对$X$和$Y$均有影响,然而,在$Z$事件成立的前提下,今天的地面情况对明天是否下雨没有影响。 -## 1.17 期望、方差、协方差、相关系数总结 +## 1.18 期望、方差、协方差、相关系数总结 **期望** ​在概率论和统计学中,数学期望(或均值,亦简称期望)是试验中每次可能结果的概率乘以其结果的总和。它反映随机变量平均取值的大小。 - 线性运算: $E(ax+by+c) = aE(x)+bE(y)+c$ -- ​推广形式: $E(\sum_{k=1}^{n}{a_kx_k+c}) = \sum_{k=1}^{n}{a_kE(x_k)+c}$ +- 推广形式: $E(\sum_{k=1}^{n}{a_ix_i+c}) = \sum_{k=1}^{n}{a_iE(x_i)+c}$ - 函数期望:设$f(x)$为$x$的函数,则$f(x)$的期望为 - 离散函数: $E(f(x))=\sum_{k=1}^{n}{f(x_k)P(x_k)}$ - 连续函数: $E(f(x))=\int_{-\infty}^{+\infty}{f(x)p(x)dx}$ @@ -354,7 +472,7 @@ $$ **方差** -​概率论中方差用来度量随机变量和其数学期望(即均值)之间的偏离程度。方差是一种特殊的期望。定义为: +概率论中方差用来度量随机变量和其数学期望(即均值)之间的偏离程度。方差是一种特殊的期望。定义为: $$ Var(x) = E((x-E(x))^2) @@ -374,7 +492,7 @@ $$ Cov(x,y)=E((x-E(x))(y-E(y))) $$ -​方差是一种特殊的协方差。当$X=Y$时,$Cov(x,y)=Var(x)=Var(y)$。 +方差是一种特殊的协方差。当$X=Y$时,$Cov(x,y)=Var(x)=Var(y)$。 > 协方差性质: > diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2-3.png" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2-3.png" deleted file mode 100644 index 2916190b..00000000 Binary files "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2-3.png" and /dev/null differ diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.1/5.jpg" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.1/5.jpg" index 3629e729..3f93149f 100644 Binary files "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.1/5.jpg" and "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.1/5.jpg" differ diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.16.17-1.png" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.16.17-1.png" new file mode 100644 index 00000000..83915ea4 Binary files /dev/null and "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.16.17-1.png" differ diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.16.17-2.png" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.16.17-2.png" new file mode 100644 index 00000000..ca5e2c41 Binary files /dev/null and "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.16.17-2.png" differ diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.16.17-3.png" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.16.17-3.png" new file mode 100644 index 00000000..511492ce Binary files /dev/null and "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.16.17-3.png" differ diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.16.18.1.png" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.16.18.1.png" new file mode 100644 index 00000000..23b150ed Binary files /dev/null and "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.16.18.1.png" differ diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.16.20.1.png" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.16.20.1.png" new file mode 100644 index 00000000..acc95fb4 Binary files /dev/null and "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.16.20.1.png" differ diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.16.4.1.jpg" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.16.4.1.jpg" new file mode 100644 index 00000000..51a16bcb Binary files /dev/null and "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.16.4.1.jpg" differ diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.16.4.2.png" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.16.4.2.png" new file mode 100644 index 00000000..d74817f7 Binary files /dev/null and "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.16.4.2.png" differ diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.16.4.3.png" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.16.4.3.png" new file mode 100644 index 00000000..42e4cee4 Binary files /dev/null and "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.16.4.3.png" differ diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.19.1.1.png" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.19.1.1.png" new file mode 100644 index 00000000..3fd7fd8f Binary files /dev/null and "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.19.1.1.png" differ diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.19.5A.jpg" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.19.5A.jpg" new file mode 100644 index 00000000..a6c5feb7 Binary files /dev/null and "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.19.5A.jpg" differ diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.19.5B.jpg" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.19.5B.jpg" new file mode 100644 index 00000000..ad455db6 Binary files /dev/null and "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.19.5B.jpg" differ diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.19.5C.png" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.19.5C.png" new file mode 100644 index 00000000..5e499e4e Binary files /dev/null and "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.19.5C.png" differ diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.2.09.png" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.2.09.png" new file mode 100644 index 00000000..94e91922 Binary files /dev/null and "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.2.09.png" differ diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.2.10.png" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.2.10.png" new file mode 100644 index 00000000..c8b9935b Binary files /dev/null and "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.2.10.png" differ diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.1/11.jpg" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.2.11.png" similarity index 58% rename from "ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.1/11.jpg" rename to "ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.2.11.png" index e615b4bc..750c2e34 100644 Binary files "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.1/11.jpg" and "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.2.11.png" differ diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.2.12.png" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.2.12.png" new file mode 100644 index 00000000..9357b0a4 Binary files /dev/null and "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.2.12.png" differ diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.2.4.png" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.2.4.png" new file mode 100644 index 00000000..e1e166dc Binary files /dev/null and "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.2.4.png" differ diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.2.8.png" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.2.8.png" new file mode 100644 index 00000000..234f4d18 Binary files /dev/null and "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.2.8.png" differ diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.20.1.jpg" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.20.1.jpg" new file mode 100644 index 00000000..efb4f6fc Binary files /dev/null and "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.20.1.jpg" differ diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.21.1.1.png" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.21.1.1.png" new file mode 100644 index 00000000..b6205fa9 Binary files /dev/null and "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.21.1.1.png" differ diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.21.1.2.png" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.21.1.2.png" new file mode 100644 index 00000000..ef734236 Binary files /dev/null and "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.21.1.2.png" differ diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.21.1.3.png" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.21.1.3.png" new file mode 100644 index 00000000..246ec05e Binary files /dev/null and "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.21.1.3.png" differ diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.21.1.4.png" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.21.1.4.png" new file mode 100644 index 00000000..70a1d786 Binary files /dev/null and "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.21.1.4.png" differ diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.21.1.5.png" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.21.1.5.png" new file mode 100644 index 00000000..61bd081e Binary files /dev/null and "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.21.1.5.png" differ diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.21.1.6.png" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.21.1.6.png" new file mode 100644 index 00000000..620857bb Binary files /dev/null and "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.21.1.6.png" differ diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.21.1.6a.png" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.21.1.6a.png" new file mode 100644 index 00000000..85755d61 Binary files /dev/null and "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.21.1.6a.png" differ diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.21.1.7.png" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.21.1.7.png" new file mode 100644 index 00000000..40fbf900 Binary files /dev/null and "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.21.1.7.png" differ diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.21.3.1.png" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.21.3.1.png" new file mode 100644 index 00000000..1b7c8051 Binary files /dev/null and "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.21.3.1.png" differ diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.40.3/1.jpg" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.40.3/1.jpg" new file mode 100644 index 00000000..51a16bcb Binary files /dev/null and "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.40.3/1.jpg" differ diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.40.3/2.20.1.jpg" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.40.3/2.20.1.jpg" new file mode 100644 index 00000000..05e9ebe2 Binary files /dev/null and "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.40.3/2.20.1.jpg" differ diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.40.3/2.png" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.40.3/2.png" index e5c69de4..d74817f7 100644 Binary files "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.40.3/2.png" and "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.40.3/2.png" differ diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.40.3/3.png" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.40.3/3.png" index ef3d80a6..42e4cee4 100644 Binary files "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.40.3/3.png" and "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.40.3/3.png" differ diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.5.1.png" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.5.1.png" new file mode 100644 index 00000000..3eb29bcd Binary files /dev/null and "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.5.1.png" differ diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.7.3.png" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.7.3.png" new file mode 100644 index 00000000..98257154 Binary files /dev/null and "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/img/ch2/2.7.3.png" differ diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/modify_log.txt" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/modify_log.txt" index f0784f11..c5e0e582 100644 --- "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/modify_log.txt" +++ "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/modify_log.txt" @@ -18,7 +18,3 @@ modify_log---->用来记录修改日志 3. 修改modify内容 4. 修改章节内容,图片路径等 -<----qjhuang-2019-3-15----> -1. 修改2.4错别字 -2. 修改3错别字 - diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/\347\254\254\344\272\214\347\253\240_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200.md" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/\347\254\254\344\272\214\347\253\240_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200.md" index 840a6527..804473f4 100644 --- "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/\347\254\254\344\272\214\347\253\240_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200.md" +++ "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/\347\254\254\344\272\214\347\253\240_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200.md" @@ -1,43 +1,41 @@ - [TOC] # 第二章 机器学习基础 -## 2.1 各种常见算法图示 +## 2.1 大话理解机器学习本质 -|回归算法|基于实例的算法|正则化方法| +​ 机器学习(Machine Learning, ML),顾名思义,让机器去学习。这里,机器指的是计算机,是算法运行的物理载体,你也可以把各种算法本身当做一个有输入和输出的机器。那么到底让计算机去学习什么呢?对于一个任务及其表现的度量方法,设计一种算法,让算法能够提取中数据所蕴含的规律,这就叫机器学习。如果输入机器的数据是带有标签的,就称作有监督学习。如果数据是无标签的,就是无监督学习。 + +## 2.2 各种常见算法图示 + +|回归算法|聚类算法|正则化方法| |:-:|:-:|:-:| |![](./img/ch2/2.1/1.jpg)|![](./img/ch2/2.1/2.jpg)|![](./img/ch2/2.1/3.jpg)| |决策树学习|贝叶斯方法|基于核的算法| |:-:|:-:|:-:| -|![](./img/ch2/2.1/4.png)|![](./img/ch2/2.1/5.jpg)|![](./img/ch2/2.1/6.jpg)| +|![](./img/ch2/2.2.4.png)|![](./img/ch2/2.1/5.jpg)|![](./img/ch2/2.1/6.jpg)| |聚类算法|关联规则学习|人工神经网络| |:-:|:-:|:-:| -|![](./img/ch2/2.1/7.jpg)|![](./img/ch2/2.1/8.jpg)|![](./img/ch2/2.1/9.png)| +|![](./img/ch2/2.1/7.jpg)|![](./img/ch2/2.2.8.png)|![](./img/ch2/2.2.09.png)| |深度学习|降低维度算法|集成算法| |:-:|:-:|:-:| -|![](./img/ch2/2.1/10.jpg)|![](./img/ch2/2.1/11.jpg)|![](./img/ch2/2.1/12.jpg)| +|![](./img/ch2/2.2.10.png)|![](./img/ch2/2.2.11.png)|![](./img/ch2/2.2.12.png)| -## 2.2 监督学习、非监督学习、半监督学习、弱监督学习? -根据数据类型的不同,对一个问题的建模有不同的方式。依据不同的学习方式和输入数据,机器学习主要分为以下四种学习方式。 +## 2.3 监督学习、非监督学习、半监督学习、弱监督学习? +​ 根据数据类型的不同,对一个问题的建模有不同的方式。依据不同的学习方式和输入数据,机器学习主要分为以下四种学习方式。 **监督学习**: -1. 监督学习是使用已知正确答案的示例来训练网络。已知数据和其一一对应的标签,训练一个智能算法,将输入数据映射到标签的过程。 +1. 监督学习是使用已知正确答案的示例来训练网络。已知数据和其一一对应的标签,训练一个预测模型,将输入数据映射到标签的过程。 2. 监督式学习的常见应用场景如分类问题和回归问题。 -3. 常见算法有逻辑回归(Logistic Regression)和反向传递神经网络(Back Propagation Neural Network) +3. 常见的有监督机器学习算法包括支持向量机(Support Vector Machine, SVM), 朴素贝叶斯(Naive Bayes), 逻辑斯谛回归(Logistic Regression),K近邻(K-Nearest Neighborhood, KNN),决策树(Decision Tree),随机森林(Random Forest),AdaBoost以及线性判别分析(Linear Discriminant Analysis,LDA)等。深度学习(Deep Learning)也是大多数以监督学习的方式呈现。 **非监督式学习**: + 1. 在非监督式学习中,数据并不被特别标识,适用于你具有数据集但无标签的情况。学习模型是为了推断出数据的一些内在结构。 2. 常见的应用场景包括关联规则的学习以及聚类等。 3. 常见算法包括Apriori算法以及k-Means算法。 @@ -48,138 +46,173 @@ 3. 常见算法如图论推理算法(Graph Inference)或者拉普拉斯支持向量机(Laplacian SVM)等。 **弱监督学习**: + 1. 弱监督学习可以看做是有多个标记的数据集合,次集合可以是空集,单个元素,或包含多种情况(没有标记,有一个标记,和有多个标记)的多个元素。 2. 数据集的标签是不可靠的,这里的不可靠可以是标记不正确,多种标记,标记不充分,局部标记等。 3. 已知数据和其一一对应的弱标签,训练一个智能算法,将输入数据映射到一组更强的标签的过程。标签的强弱指的是标签蕴含的信息量的多少,比如相对于分割的标签来说,分类的标签就是弱标签。 4. 举例,告诉一张包含气球的图片,需要得出气球在图片中的位置及气球和背景的分割线,这就是已知弱标签学习强标签的问题。 -在企业数据应用的场景下, 人们最常用的可能就是监督式学习和非监督式学习的模型。 在图像识别等领域,由于存在大量的非标识的数据和少量的可标识数据, 目前半监督式学习是一个很热的话题。 + 在企业数据应用的场景下, 人们最常用的可能就是监督式学习和非监督式学习的模型。 在图像识别等领域,由于存在大量的非标识的数据和少量的可标识数据, 目前半监督式学习是一个很热的话题。 -## 2.3 监督学习有哪些步骤 -**监督式学习**: -监督学习是使用已知正确答案的示例来训练网络。每组训练数据有一个明确的标识或结果,想象一下,我们可以训练一个网络,让其从照片库中(其中包含气球的照片)识别出气球的照片。以下就是我们在这个假设场景中所要采取的步骤。 +## 2.4 监督学习有哪些步骤 +​ 监督学习是使用已知正确答案的示例来训练网络。每组训练数据有一个明确的标识或结果,想象一下,我们可以训练一个网络,让其从照片库中(其中包含气球的照片)识别出气球的照片。以下就是我们在这个假设场景中所要采取的步骤。 **步骤1:数据集的创建和分类** -首先,浏览你的照片(数据集),确定所有包含气球的照片,并对其进行标注。然后,将所有照片分为训练集和验证集。目标就是在深度网络中找一函数,这个函数输入是任意一张照片,当照片中包含气球时,输出1,否则输出0。 -**步骤2:训练** -选择合适的模型,模型可通过以下激活函数对每张照片进行预测。既然我们已经知道哪些是包含气球的图片,那么我们就可以告诉模型它的预测是对还是错。然后我们会将这些信息反馈(feed back)给网络。 -该算法使用的这种反馈,就是一个量化“真实答案与模型预测有多少偏差”的函数的结果。这个函数被称为成本函数(cost function),也称为目标函数(objective function),效用函数(utility function)或适应度函数(fitness function)。然后,该函数的结果用于修改一个称为反向传播(backpropagation)过程中节点之间的连接强度和偏差。 -我们会为每个图片都重复一遍此操作,而在每种情况下,算法都在尽量最小化成本函数。 -其实,我们有多种数学技术可以用来验证这个模型是正确还是错误的,但我们常用的是一个非常常见的方法,我们称之为梯度下降(gradient descent)。 -**步骤3:验证** -当处理完训练集所有照片,接着要去测试该模型。利用验证集来来验证训练有素的模型是否可以准确地挑选出含有气球在内的照片。 +​ 首先,浏览你的照片(数据集),确定所有包含气球的照片,并对其进行标注。然后,将所有照片分为训练集和验证集。目标就是在深度网络中找一函数,这个函数输入是任意一张照片,当照片中包含气球时,输出1,否则输出0。 + +**步骤2: 数据增强** + +​ 当原始数据搜集和标注完毕,一般搜集的数据并不一定包含目标在各种扰动下的信息。数据的好坏对于机器学习模型的预测能力至关重要,因此一般会进行数据增强。对于图像数据来说,数据增强一般包括,图像旋转,平移,颜色变换,裁剪,仿射变换等。 + +**步骤3:特征工程** + +​ 一般来讲,特征工程包含特征提取和特征选择。常见的手工特征(hand-crafted feature)有尺度不变特征变换变描述子(Scale-invariant feature transform,SIFT),方向梯度直方图(Histogram of Oriented Gradient, *HOG*)等。由于手工特征是启发式的,其算法设计背后的出发点不同,将这些特征组合在一起的时候有可能会产生冲突,如何将组合特征的效能发挥出来,使原始数据在特征空间中的判别性最大化,就需要用到特征选择的方法。在深度学习方法大获成功之后,人们很大一部分不在关注特征工程本身。因为,最常用到的卷积神经网络(Convolutional Neural Networks, CNNs)本身就是一种特征提取和选择的引擎。研究者提出的不同的网络结构、正则化、归一化方法实际上就是深度学习背景下的特征工程。 + +**步骤4:构建预测模型和损失** + +​ 将原始数据映射到特征空间之后,也就意味着我们得到了比较合理的输入。下一步就是构建合适的预测模型得到对应输入的输出。而如何保证模型的输出和输入的标签的一致性,就需要构建模型预测和标签之间的损失函数,常见的损失函数有交叉熵、均方差等。通过优化方法不断迭代,使模型从最初的初始化状态一步步进化为有预测能力的模型的过程,实际上就是学习过程。 + +**步骤5:训练** + 选择合适的模型和超参数进行初始化,其中超参数比如支持向量机中核函数、误差项惩罚权重等。当模型初始化参数设定好后,将制作好的特征数据输入到模型,通过合适的优化方法不断缩小输出与标签之间的差距,当迭代过程到了截止条件,就可以得到训练好的模型。优化方法最常见的就是梯度下降法及其变种,使用梯度下降法的前提是优化目标函数对于模型是可导的。 + +**步骤6:验证和模型选择** + 训练完训练集图片后,需要进行模型测试。利用验证集来验证模型是否可以准确地挑选出含有气球在内的照片。 在此过程中,通常会通过调整和模型相关的各种事物(超参数)来重复步骤2和3,诸如里面有多少个节点,有多少层,哪些数学函数用于决定节点是否亮起,如何在反向传播阶段积极有效地训练权值等等。 -**步骤4:测试及应用** -当有了一个准确的模型,就可以将该模型部署到你的应用程序中。你可以将模型定义为API调用,并且你可以从软件中调用该方法,从而进行推理并给出相应的结果。 +**步骤7:测试及应用** + 当有了一个准确的模型,就可以将该模型部署到你的应用程序中。你可以将模型定义为API调用,并且你可以从软件中调用该方法,从而进行推理并给出相应的结果。 ## 2.4 多实例学习? -多实例学习(multiple instance learning) :已知包含多个数据的数据包和数据包的标签,训练智能算法,将数据包映射到标签的过程,在有的问题中也同时给出包内每个数据的标签。 -比如说一段视频由很多张图组成,假如10000张,那么我们要判断视频里是否包含某一物体,比如气球。单张标注每一帧是否有气球太耗时,通常人们看一遍说这个视频里是否有气球,就得到了多实例学习的数据。10000帧的数据不是每一个都有气球出现,只要有一帧有气球,那么我们就认为这个数据包是有气球的。只有当所有的视频帧都没有气球,才是没有气球的。从这里面学习哪一段视频(10000张)是否有气球出现就是多实例学习的问题。 +​ 多实例学习(multiple instance learning) :已知包含多个数据的数据包和数据包的标签,训练智能算法,将数据包映射到标签的过程,在有的问题中也同时给出包内每个数据的标签。 +比如说一段视频由很多张图组成,假如10000张,那么我们要判断视频里是否包含某一物体,比如气球。单张标注每一帧是否有气球太耗时,通常人们看一遍说这个视频里是否有气球,就得到了多示例学习的数据。10000帧的数据不是每一个都有气球出现,只要有一帧有气球,那么我们就认为这个数据包是有气球的。只有当所有的视频帧都没有气球,才是没有气球的。从这里面学习哪一段视频(10000张)是否有气球出现就是多实例学习的问题。 -## 2.5 分类网络和回归的区别? -2.3小节介绍了包含气球照片的数据集整理。当照片中包含气球时,输出1,否则输出0。此步骤通常称为分类任务(categorization task)。在这种情况下,我们进行的通常是一个结果为yes or no的训练。 -但事实上,监督学习也可以用于输出一组值,而不仅仅是0或1。例如,我们可以训练一个网络,用它来输出一张图片上有气球的概率,那么在这种情况下,输出值就是0到1之间的任意值。这些任务我们称之为回归。 - -## 2.6 什么是神经网络? -神经网络就是按照一定规则将多个神经元连接起来的网络。不同的神经网络,具有不同的连接规则。 +## 2.5 什么是神经网络? +​ 神经网络就是按照一定规则将多个神经元连接起来的网络。不同的神经网络,具有不同的连接规则。 例如全连接(full connected, FC)神经网络,它的规则包括: + 1. 有三种层:输入层,输出层,隐藏层。 2. 同一层的神经元之间没有连接。 -3. full connected的含义:第 N 层的每个神经元和第 N-1 层的所有神经元相连,第 N-1 层神经元的输出就是第 N 层神经元的输入。 +3. fully connected的含义:第 N 层的每个神经元和第 N-1 层的所有神经元相连,第 N-1 层神经元的输出就是第 N 层神经元的输入。 4. 每个连接都有一个权值。 -**神经网络架构** -下面这张图就是一个神经网络系统,它由很多层组成。输入层负责接收信息,比如一只猫的图片。输出层是计算机对这个输入信息的判断结果,它是不是猫。隐藏层就是对输入信息的传递和加工处理。 -![](./img/ch2/2.6/1.png) + **神经网络架构** + 下面这张图就是一个神经网络系统,它由很多层组成。输入层负责接收信息,比如一只猫的图片。输出层是计算机对这个输入信息的判断结果,它是不是猫。隐藏层就是对输入信息的传递和加工处理。 + ![](./img/ch2/2.5.1.png) -## 2.7 理解局部最优与全局最优 +## 2.6 理解局部最优与全局最优 -笑谈局部最优和全局最优 +​ 笑谈局部最优和全局最优 > 柏拉图有一天问老师苏格拉底什么是爱情?苏格拉底叫他到麦田走一次,摘一颗最大的麦穗回来,不许回头,只可摘一次。柏拉图空着手出来了,他的理由是,看见不错的,却不知道是不是最好的,一次次侥幸,走到尽头时,才发现还不如前面的,于是放弃。苏格拉底告诉他:“这就是爱情。”这故事让我们明白了一个道理,因为生命的一些不确定性,所以全局最优解是很难寻找到的,或者说根本就不存在,我们应该设置一些限定条件,然后在这个范围内寻找最优解,也就是局部最优解——有所斩获总比空手而归强,哪怕这种斩获只是一次有趣的经历。 -> 柏拉图有一天又问什么是婚姻?苏格拉底叫他到彬树林走一次,选一棵最好的树做圣诞树,也是不许回头,只许选一次。这次他一身疲惫地拖了一棵看起来直挺、翠绿,却有点稀疏的杉树回来,他的理由是,有了上回的教训,好不容易看见一棵看似不错的,又发现时间、体力已经快不够用了,也不管是不是最好的,就拿回来了。苏格拉底告诉他:“这就是婚姻。 +> 柏拉图有一天又问什么是婚姻?苏格拉底叫他到树林走一次,选一棵最好的树做圣诞树,也是不许回头,只许选一次。这次他一身疲惫地拖了一棵看起来直挺、翠绿,却有点稀疏的杉树回来,他的理由是,有了上回的教训,好不容易看见一棵看似不错的,又发现时间、体力已经快不够用了,也不管是不是最好的,就拿回来了。苏格拉底告诉他:“这就是婚姻。 -优化问题一般分为局部最优和全局最优。 +​ 优化问题一般分为局部最优和全局最优。 1. 局部最优,就是在函数值空间的一个有限区域内寻找最小值;而全局最优,是在函数值空间整个区域寻找最小值问题。 -2. 函数局部最小点是那种它的函数值小于或等于附近点的点。但是有可能大于较远距离的点。 +2. 函数局部最小点是它的函数值小于或等于附近点的点。但是有可能大于较远距离的点。 3. 全局最小点是那种它的函数值小于或等于所有的可行点。 -## 2.8 分类算法 +## 2.7 分类算法 + +​ 分类算法和回归算法是对真实世界不同建模的方法。分类模型是认为模型的输出是离散的,例如大自然的生物被划分为不同的种类,是离散的。回归模型的输出是连续的,例如的人的身高变化过程是一个连续过程,而不是离散的。 -### 2.8.1 常用分类算法的优缺点? +​ 因此,在实际建模过程时,采用分类模型还是回归模型,取决于你对任务(真实世界)的分析和理解。 + +### 2.7.1 常用分类算法的优缺点? |算法|优点|缺点| |:-|:-|:-| -|Bayes 贝叶斯分类法|1)所需估计的参数少,对于缺失数据不敏感。2)有着坚实的数学基础,以及稳定的分类效率。|1)假设属性之间相互独立,这往往并不成立。(喜欢吃番茄、鸡蛋,却不喜欢吃番茄炒蛋)。2)需要知道先验概率。3)分类决策存在错误率。| -|Decision Tree决策树|1)不需要任何领域知识或参数假设。2)适合高维数据。3)简单易于理解。4)短时间内处理大量数据,得到可行且效果较好的结果。5)能够同时处理数据型和常规性属性。|1)对于各类别样本数量不一致数据,信息增益偏向于那些具有更多数值的特征。2)易于过拟合。3)忽略属性之间的相关性。4)不支持在线学习。| -|SVM支持向量机|1)可以解决小样本下机器学习的问题。2)提高泛化性能。3)可以解决高维、非线性问题。超高维文本分类仍受欢迎。4)避免神经网络结构选择和局部极小的问题。|1)对缺失数据敏感。2)内存消耗大,难以解释。3)运行和调差略烦人。| -|KNN K近邻|1)思想简单,理论成熟,既可以用来做分类也可以用来做回归; 2)可用于非线性分类; 3)训练时间复杂度为O(n); 4)准确度高,对数据没有假设,对outlier不敏感;|1)计算量太大2)对于样本分类不均衡的问题,会产生误判。3)需要大量的内存。4)输出的可解释性不强。| -|Logistic Regression逻辑回归|1)速度快。2)简单易于理解,直接看到各个特征的权重。3)能容易地更新模型吸收新的数据。4)如果想要一个概率框架,动态调整分类阀值。|特征处理复杂。需要归一化和较多的特征工程。| -|Neural Network 神经网络|1)分类准确率高。2)并行处理能力强。3)分布式存储和学习能力强。4)鲁棒性较强,不易受噪声影响。|1)需要大量参数(网络拓扑、阀值、阈值)。2)结果难以解释。3)训练时间过长。| -|Adaboosting|1)adaboost是一种有很高精度的分类器。2)可以使用各种方法构建子分类器,Adaboost算法提供的是框架。3)当使用简单分类器时,计算出的结果是可以理解的。而且弱分类器构造极其简单。4)简单,不用做特征筛选。5)不用担心overfitting。|对outlier比较敏感| - -### 2.8.2 正确率能很好的评估分类算法吗? -不同算法有不同特点,在不同数据集上有不同的表现效果,根据特定的任务选择不同的算法。如何评价分类算法的好坏,要做具体任务具体分析。对于决策树,主要用正确率去评估,但是其他算法,只用正确率能很好的评估吗? -答案是否定的。 -正确率确实是一个很直观很好的评价指标,但是有时候正确率高并不能完全代表一个算法就好。比如对某个地区进行地震预测,地震分类属性分为0:不发生地震、1发生地震。我们都知道,不发生的概率是极大的,对于分类器而言,如果分类器不加思考,对每一个测试样例的类别都划分为0,达到99%的正确率,但是,问题来了,如果真的发生地震时,这个分类器毫无察觉,那带来的后果将是巨大的。很显然,99%正确率的分类器并不是我们想要的。出现这种现象的原因主要是数据分布不均衡,类别为1的数据太少,错分了类别1但达到了很高的正确率缺忽视了研究者本身最为关注的情况。 - -### 2.8.3 分类算法的评估方法? -1. **几个常用的术语** -这里首先介绍几个*常见*的 模型评价术语,现在假设我们的分类目标只有两类,计为正例(positive)和负例(negative)分别是: - 1) True positives(TP): 被正确地划分为正例的个数,即实际为正例且被分类器划分为正例的实例数(样本数); - 2) False positives(FP): 被错误地划分为正例的个数,即实际为负例但被分类器划分为正例的实例数; - 3) False negatives(FN):被错误地划分为负例的个数,即实际为正例但被分类器划分为负例的实例数; - 4) True negatives(TN): 被正确地划分为负例的个数,即实际为负例且被分类器划分为负例的实例数。  +|Bayes 贝叶斯分类法|1)所需估计的参数少,对于缺失数据不敏感。
2)有着坚实的数学基础,以及稳定的分类效率。|1)假设属性之间相互独立,这往往并不成立。(喜欢吃番茄、鸡蛋,却不喜欢吃番茄炒蛋)。
2)需要知道先验概率。
3)分类决策存在错误率。| +|Decision Tree决策树|1)不需要任何领域知识或参数假设。
2)适合高维数据。
3)简单易于理解。
4)短时间内处理大量数据,得到可行且效果较好的结果。
5)能够同时处理数据型和常规性属性。|1)对于各类别样本数量不一致数据,信息增益偏向于那些具有更多数值的特征。
2)易于过拟合。
3)忽略属性之间的相关性。
4)不支持在线学习。| +|SVM支持向量机|1)可以解决小样本下机器学习的问题。
2)提高泛化性能。
3)可以解决高维、非线性问题。超高维文本分类仍受欢迎。
4)避免神经网络结构选择和局部极小的问题。|1)对缺失数据敏感。
2)内存消耗大,难以解释。
3)运行和调差略烦人。| +|KNN K近邻|1)思想简单,理论成熟,既可以用来做分类也可以用来做回归;
2)可用于非线性分类;
3)训练时间复杂度为O(n);
4)准确度高,对数据没有假设,对outlier不敏感;|1)计算量太大。
2)对于样本分类不均衡的问题,会产生误判。
3)需要大量的内存。
4)输出的可解释性不强。| +|Logistic Regression逻辑回归|1)速度快。
2)简单易于理解,直接看到各个特征的权重。
3)能容易地更新模型吸收新的数据。
4)如果想要一个概率框架,动态调整分类阀值。|特征处理复杂。需要归一化和较多的特征工程。| +|Neural Network 神经网络|1)分类准确率高。
2)并行处理能力强。
3)分布式存储和学习能力强。
4)鲁棒性较强,不易受噪声影响。|1)需要大量参数(网络拓扑、阀值、阈值)。
2)结果难以解释。
3)训练时间过长。| +|Adaboosting|1)adaboost是一种有很高精度的分类器。
2)可以使用各种方法构建子分类器,Adaboost算法提供的是框架。
3)当使用简单分类器时,计算出的结果是可以理解的。而且弱分类器构造极其简单。
4)简单,不用做特征筛选。
5)不用担心overfitting。|对outlier比较敏感| + + + +### 2.7.2 分类算法的评估方法? +- **几个常用术语** + 这里首先介绍几个常见的模型评价术语,现在假设我们的分类目标只有两类,计为正例(positive)和负例(negative)分别是: + 1) True positives(TP): 被正确地划分为正例的个数,即实际为正例且被分类器划分为正例的实例数; + 2) False positives(FP): 被错误地划分为正例的个数,即实际为负例但被分类器划分为正例的实例数; + 3) False negatives(FN):被错误地划分为负例的个数,即实际为正例但被分类器划分为负例的实例数; + 4) True negatives(TN): 被正确地划分为负例的个数,即实际为负例且被分类器划分为负例的实例数。  ![](./img/ch2/2.9/1.png) -上图是这四个术语的混淆矩阵。 -1)P=TP+FN表示实际为正例的样本个数。 -2)True、False描述的是分类器是否判断正确。 -3)Positive、Negative是分类器的分类结果,如果正例计为1、负例计为-1,即positive=1、negative=-1。用1表示True,-1表示False,那么实际的类标=TF\*PN,TF为true或false,PN为positive或negative。 -4)例如True positives(TP)的实际类标=1\*1=1为正例,False positives(FP)的实际类标=(-1)\*1=-1为负例,False negatives(FN)的实际类标=(-1)\*(-1)=1为正例,True negatives(TN)的实际类标=1\*(-1)=-1为负例。 - -2. **评价指标** - 1) 正确率(accuracy) - 正确率是我们最常见的评价指标,accuracy = (TP+TN)/(P+N),正确率是被分对的样本数在所有样本数中的占比,通常来说,正确率越高,分类器越好。 - 2) 错误率(error rate) - 错误率则与正确率相反,描述被分类器错分的比例,error rate = (FP+FN)/(P+N),对某一个实例来说,分对与分错是互斥事件,所以accuracy =1 - error rate。 - 3) 灵敏度(sensitive) - sensitive = TP/P,表示的是所有正例中被分对的比例,衡量了分类器对正例的识别能力。 - 4) 特效度(specificity) - specificity = TN/N,表示的是所有负例中被分对的比例,衡量了分类器对负例的识别能力。 - 5) 精度(precision) - 精度是精确性的度量,表示被分为正例的示例中实际为正例的比例,precision=TP/(TP+FP)。 - 6) 召回率(recall) - 召回率是覆盖面的度量,度量有多个正例被分为正例,recall=TP/(TP+FN)=TP/P=sensitive,可以看到召回率与灵敏度是一样的。 - 7) 其他评价指标 - 计算速度:分类器训练和预测需要的时间; - 鲁棒性:处理缺失值和异常值的能力; - 可扩展性:处理大数据集的能力; - 可解释性:分类器的预测标准的可理解性,像决策树产生的规则就是很容易理解的,而神经网络的一堆参数就不好理解,我们只好把它看成一个黑盒子。 - 8) 查准率和查全率反映了分类器分类性能的两个方面。如果综合考虑查准率与查全率,可以得到新的评价指标F1测试值,也称为综合分类率:$F1=\frac{2 \times precision \times recall}{precision + recall}$ - 为了综合多个类别的分类情况,评测系统整体性能,经常采用的还有微平均F1(micro-averaging)和宏平均F1(macro-averaging )两种指标。宏平均F1与微平均F1是以两种不同的平均方式求的全局的F1指标。其中宏平均F1的计算方法先对每个类别单独计算F1值,再取这些F1值的算术平均值作为全局指标。而微平均F1的计算方法是先累加计算各个类别的a、b、c、d的值,再由这些值求出F1值。由两种平均F1的计算方式不难看出,宏平均F1平等对待每一个类别,所以它的值主要受到稀有类别的影响,而微平均F1平等考虑文档集中的每一个文档,所以它的值受到常见类别的影响比较大。 - **ROC曲线和PR曲线** - -References -[1] 李航. 统计学习方法[M]. 北京:清华大学出版社,2012. - -### 2.8.4 什么样的分类器是最好的? -对某一个任务,某个具体的分类器不可能同时满足或提高所有上面介绍的指标。 -如果一个分类器能正确分对所有的实例,那么各项指标都已经达到最优,但这样的分类器往往不存在。比如之前说的地震预测,既然不能百分百预测地震的发生,但实际情况中能容忍一定程度的误报。假设在1000次预测中,共有5次预测发生了地震,真实情况中有一次发生了地震,其他4次则为误报。正确率由原来的999/1000=99.9下降为996/1000=99.6。召回率由0/1=0%上升为1/1=100%。对此解释为,虽然预测失误了4次,但真的地震发生前,分类器能预测对,没有错过,这样的分类器实际意义更为重大,正是我们想要的。在这种情况下,在一定正确率前提下,要求分类器的召回率尽量高。 - -## 2.9 逻辑回归 - -### 2.9.1 理解逻辑回归 - -**回归划分**: +上图是这四个术语的混淆矩阵,做以下说明: + 1)P=TP+FN表示实际为正例的样本个数。 + 2)True、False描述的是分类器是否判断正确。 + 3)Positive、Negative是分类器的分类结果,如果正例计为1、负例计为-1,即positive=1、negative=-1。用1表示True,-1表示False,那么实际的类标=TF\*PN,TF为true或false,PN为positive或negative。 + 4)例如True positives(TP)的实际类标=1\*1=1为正例,False positives(FP)的实际类标=(-1)\*1=-1为负例,False negatives(FN)的实际类标=(-1)\*(-1)=1为正例,True negatives(TN)的实际类标=1\*(-1)=-1为负例。 + + + +- **评价指标** + 1) 正确率(accuracy) + 正确率是我们最常见的评价指标,accuracy = (TP+TN)/(P+N),正确率是被分对的样本数在所有样本数中的占比,通常来说,正确率越高,分类器越好。 + 2) 错误率(error rate) + 错误率则与正确率相反,描述被分类器错分的比例,error rate = (FP+FN)/(P+N),对某一个实例来说,分对与分错是互斥事件,所以accuracy =1 - error rate。 + 3) 灵敏度(sensitivity) + sensitivity = TP/P,表示的是所有正例中被分对的比例,衡量了分类器对正例的识别能力。 + 4) 特异性(specificity) + specificity = TN/N,表示的是所有负例中被分对的比例,衡量了分类器对负例的识别能力。 + 5) 精度(precision) + precision=TP/(TP+FP),精度是精确性的度量,表示被分为正例的示例中实际为正例的比例。 + 6) 召回率(recall) + 召回率是覆盖面的度量,度量有多个正例被分为正例,recall=TP/(TP+FN)=TP/P=sensitivity,可以看到召回率与灵敏度是一样的。 + 7) 其他评价指标 + 计算速度:分类器训练和预测需要的时间; + 鲁棒性:处理缺失值和异常值的能力; + 可扩展性:处理大数据集的能力; + 可解释性:分类器的预测标准的可理解性,像决策树产生的规则就是很容易理解的,而神经网络的一堆参数就不好理解,我们只好把它看成一个黑盒子。 + 8) 精度和召回率反映了分类器分类性能的两个方面。如果综合考虑查准率与查全率,可以得到新的评价指标F1-score,也称为综合分类率:$F1=\frac{2 \times precision \times recall}{precision + recall}​$。 + +​ 为了综合多个类别的分类情况,评测系统整体性能,经常采用的还有微平均F1(micro-averaging)和宏平均F1(macro-averaging )两种指标。 + +​ (1)宏平均F1与微平均F1是以两种不同的平均方式求的全局F1指标。 + +​ (2)宏平均F1的计算方法先对每个类别单独计算F1值,再取这些F1值的算术平均值作为全局指标。 + +​ (3)微平均F1的计算方法是先累加计算各个类别的a、b、c、d的值,再由这些值求出F1值。 + +​ (4)由两种平均F1的计算方式不难看出,宏平均F1平等对待每一个类别,所以它的值主要受到稀有类别的影响,而微平均F1平等考虑文档集中的每一个文档,所以它的值受到常见类别的影响比较大。 + + + +- **ROC曲线和PR曲线** + +​ ROC曲线是(receiver operating characteristic curve,受试者工作特征曲线)的简称,是以灵敏度(真阳性率)为纵坐标,以1-特异性(假阳性率)为横坐标绘制的性能评价曲线。可以将不同模型对同一数据集的ROC曲线绘制在同一笛卡尔坐标系中,ROC曲线越靠近左上角,说明其对应模型越可靠。也可以通过ROC曲线下面的面积(area under curve, AUC)来评价模型,AUC越大,模型越可靠。 + +![](./img/ch2/2.7.3.png) + +​ 图2.7.3 ROC曲线 + +​ PR曲线是Precision recall curve的简称,描述的是precision和recall之间的关系,以recall为横坐标,precision为纵坐标绘制的曲线。该曲线的所对应的面积AUC实际上是目标检测中常用的评价指标平均精度(Average Precision, AP)。AP越高,说明模型性能越好。 + +### 2.7.3 正确率能很好的评估分类算法吗? + +​ 不同算法有不同特点,在不同数据集上有不同的表现效果,根据特定的任务选择不同的算法。如何评价分类算法的好坏,要做具体任务具体分析。对于决策树,主要用正确率去评估,但是其他算法,只用正确率能很好的评估吗? +​ 答案是否定的。 +​ 正确率确实是一个很直观很好的评价指标,但是有时候正确率高并不能完全代表一个算法就好。比如对某个地区进行地震预测,地震分类属性分为0:不发生地震、1发生地震。我们都知道,不发生的概率是极大的,对于分类器而言,如果分类器不加思考,对每一个测试样例的类别都划分为0,达到99%的正确率,但是,问题来了,如果真的发生地震时,这个分类器毫无察觉,那带来的后果将是巨大的。很显然,99%正确率的分类器并不是我们想要的。出现这种现象的原因主要是数据分布不均衡,类别为1的数据太少,错分了类别1但达到了很高的正确率缺忽视了研究者本身最为关注的情况。 + +### 2.7.4 什么样的分类器是最好的? +​ 对某一个任务,某个具体的分类器不可能同时满足或提高所有上面介绍的指标。 +​ 如果一个分类器能正确分对所有的实例,那么各项指标都已经达到最优,但这样的分类器往往不存在。比如之前说的地震预测,既然不能百分百预测地震的发生,但实际情况中能容忍一定程度的误报。假设在1000次预测中,共有5次预测发生了地震,真实情况中有一次发生了地震,其他4次则为误报。正确率由原来的999/1000=99.9下降为996/10000=99.6。召回率由0/1=0%上升为1/1=100%。对此解释为,虽然预测失误了4次,但真的地震发生前,分类器能预测对,没有错过,这样的分类器实际意义更为重大,正是我们想要的。在这种情况下,在一定正确率前提下,要求分类器的召回率尽量高。 + +## 2.8 逻辑回归 + +### 2.8.1 回归划分 + 广义线性模型家族里,依据因变量不同,可以有如下划分: + 1. 如果是连续的,就是多重线性回归; 2. 如果是二项分布,就是Logistic回归; 3. 如果是Poisson分布,就是Poisson回归; 4. 如果是负二项分布,就是负二项回归。 -Logistic回归的因变量可以是二分类的,也可以是多分类的,但是二分类的更为常用,也更加容易解释。所以实际中最常用的就是二分类的Logistic回归。 +5. Logistic回归的因变量可以是二分类的,也可以是多分类的,但是二分类的更为常用,也更加容易解释。所以实际中最常用的就是二分类的Logistic回归。 + +### 2.8.2 逻辑回归适用性 -**Logistic回归的适用性**: 1. 用于概率预测。用于可能性预测时,得到的结果有可比性。比如根据模型进而预测在不同的自变量情况下,发生某病或某种情况的概率有多大; 2. 用于分类。实际上跟预测有些类似,也是根据模型,判断某人属于某病或属于某种情况的概率有多大,也就是看一下这个人有多大的可能性是属于某病。进行分类时,仅需要设定一个阈值即可,可能性高于阈值是一类,低于阈值是另一类。 3. 寻找危险因素。寻找某一疾病的危险因素等。 @@ -192,7 +225,9 @@ Logistic回归的因变量可以是二分类的,也可以是多分类的,但 3. 朴素贝叶斯需要独立假设。 4. 逻辑回归需要求特征参数间是线性的。 -### 2.9.3线性回归与逻辑回归的区别?(贡献者:黄钦建-华南理工大学) +### 2.9.3线性回归与逻辑回归的区别? + +(贡献者:黄钦建-华南理工大学) 线性回归的样本的输出,都是连续值,$ y\in (-\infty ,+\infty )$,而逻辑回归中$y\in (0,1)$,只能取0和1。 @@ -203,7 +238,7 @@ Logistic回归的因变量可以是二分类的,也可以是多分类的,但 逻辑回归:$f(x)=P(y=1|x;\theta )=g(\theta ^{T}x)$,其中,$g(z)=\frac{1}{1+e^{-z}}$ -可以看出,线性回归的拟合函数,是对f(x)的输出变量y的拟合,而逻辑回归的拟合函数是对为1类的样本的概率的拟合。 +可以看出,线性回归的拟合函数,是对f(x)的输出变量y的拟合,而逻辑回归的拟合函数是对为1类样本的概率的拟合。 那么,为什么要以1类样本的概率进行拟合呢,为什么可以这样拟合呢? @@ -212,9 +247,9 @@ $\theta ^{T}x=0$就相当于是1类和0类的决策边界: 当$\theta ^{T}x>0$,则y>0.5;若$\theta ^{T}x\rightarrow +\infty $,则$y \rightarrow 1 $,即y为1类; -当$\theta ^{T}x<0$,则y<0.5;若$\theta ^{T}x\rightarrow -\infty $,则$y \rightarrow 0 $,即y为0类; +当$\theta ^{T}x<0​$,则y<0.5;若$\theta ^{T}x\rightarrow -\infty ​$,则$y \rightarrow 0 ​$,即y为0类; -这个时候就能看出区别来了,在线性回归中$\theta ^{T}x$为预测值的拟合函数;而在逻辑回归中$\theta ^{T}x$为决策边界。 +这个时候就能看出区别,在线性回归中$\theta ^{T}x$为预测值的拟合函数;而在逻辑回归中$\theta ^{T}x​$为决策边界。 | | 线性回归 | 逻辑回归 | |:-------------:|:-------------:|:-----:| @@ -226,24 +261,9 @@ $\theta ^{T}x=0$就相当于是1类和0类的决策边界: 下面具体解释一下: -1. 拟合函数和预测函数什么关系呢?其实就是将拟合函数做了一个逻辑函数的转换,转换后使得$y^{(i)} \in (0,1)$; +1. 拟合函数和预测函数什么关系呢?简单来说就是将拟合函数做了一个逻辑函数的转换,转换后使得$y^{(i)} \in (0,1)$; 2. 最小二乘和最大似然估计可以相互替代吗?回答当然是不行了。我们来看看两者依仗的原理:最大似然估计是计算使得数据出现的可能性最大的参数,依仗的自然是Probability。而最小二乘是计算误差损失。 -### 2.9.4 Factorization Machines(FM)模型原理 -1. FM旨在解决稀疏数据的特征组合问题,某些特征经过关联之后,就会与label之间的相关性就会提高,例如设备id与ip地址之间的特征交叉就会更好的与label之间有相关性. -2. FM为二阶多项式模型 - * 假设有D维特征,𝑥 , ... , 𝑥 ,若采用线性模型,则 -$y = w_{0} +\sum_{j = 1}^{D} w_{i}x_{j}$ - * 若考虑二阶特征组合,得到模型 -$y = w_{0} +\sum_{j = 1}^{D} w_{i}x_{j} + \sum_{i = 1}^{D}\sum_{j = i + 1}^{D}w_{ij}x_{i}x_{j}$ - * 组合特征的参数一共有D(D-1)/2个,任意两个参数都是独立的 - * 数据稀疏使得二次项参数的训练很困难: - * 每个样本都需要大量非0的$x_{j}$和$x_{i}$样本 - * 训练样本不足会导致$w_{ij}$不准确 - * FM采用类似model-based协同过滤中的矩阵分解方式对二次多项式的系数进行有效表示: -$y = w_{0} +\sum_{j = 1}^{D} w_{i}x_{j} + \sum_{i = 1}^{D}\sum_{j = i + 1}^{D}x_{i}x_{j}$ - * FM为进一步对隐含向量只取K维,从而$ = \sum_{k = 1}^{K} v_{i,k}v_{j,k}$ - * 二项式参数之前的D(D-1)/2变成了KD个,大大降低了计算量。 ## 2.10 代价函数 ### 2.10.1 为什么需要代价函数? @@ -259,27 +279,26 @@ h(x) = A + Bx $$ 假设函数中有$A$和$B$两个参数,当参数发生变化时,假设函数状态也会随着变化。 -如下图所示 +如下图所示: ![](./img/ch2/2.16/1.jpg) -想要你和图中的离散点,我们需要尽可能找到最优的$A$和$B$来使这条直线更能代表所有数据。如何找到最优解呢,这就需要使用代价函数来求解,以平方误差代价函数为例,假设函数为$h(x)=\theta_0x$。 -平方误差代价函数的主要思想 -平方误差代价函数的主要思想就是将实际数据给出的值与拟合出的线的对应值做差,求出拟合出的直线与实际的差距。在实际应用中,为了避免因个别极端数据产生的影响,采用类似方差再取二分之一的方式来减小个别数据的影响。因此,引出代价函数: - +​ 想要拟合图中的离散点,我们需要尽可能找到最优的$A$和$B$来使这条直线更能代表所有数据。如何找到最优解呢,这就需要使用代价函数来求解,以平方误差代价函数为例,假设函数为$h(x)=\theta_0x$。 +​ **平方误差代价函数的主要思想** +​ 平方误差代价函数的主要思想就是将实际数据给出的值与拟合出的线的对应值做差,求出拟合出的直线与实际的差距。在实际应用中,为了避免因个别极端数据产生的影响,采用类似方差再取二分之一的方式来减小个别数据的影响。因此,引出代价函数: $$ J(\theta_0, \theta_1) = \frac{1}{m}\sum_{i=1}^m(h(x^{(i)})-y^{(i)})^2 $$ -**最优解即为代价函数的最小值**$\min J(\theta_0, \theta_1)$。如果是1个参数,代价函数一般通过二维曲线便可直观看出。如果是2个参数,代价函数通过三维图像可看出效果,参数越多,越复杂。 +**最优解即为代价函数的最小值**$\min J(\theta_0, \theta_1)​$。如果是1个参数,代价函数一般通过二维曲线便可直观看出。如果是2个参数,代价函数通过三维图像可看出效果,参数越多,越复杂。 当参数为2个时,代价函数是三维图像。 ![](./img/ch2/2.16/2.jpg) ### 2.10.3 为什么代价函数要非负? -目标函数存在一个下界,在优化过程当中,如果优化算法能够使目标函数不断减小,根据单调有界准则,这个优化算法就能证明是收敛有效的。 -只要设计的目标函数有下界,基本上都可以,代价函数非负更为方便。 +​ 目标函数存在一个下界,在优化过程当中,如果优化算法能够使目标函数不断减小,根据单调有界准则,这个优化算法就能证明是收敛有效的。 +​ 只要设计的目标函数有下界,基本上都可以,代价函数非负更为方便。 ### 2.10.4 常见代价函数? 1. **二次代价函数(quadratic cost)**: @@ -288,53 +307,51 @@ $$ J = \frac{1}{2n}\sum_x\Vert y(x)-a^L(x)\Vert^2 $$ -其中,$J$表示代价函数,$x$表示样本,$y$示实际值,$a$表示输出值,$n$表示样本的总数。使用一个样本为例简单说明,此时二次代价函数为: - -$$J = \frac{(y-a)^2}{2}$$ - -假如使用梯度下降法(Gradient descent)来调整权值参数的大小,权值$w$和偏置$b$的梯度推导如下: - -$$\frac{\delta J}{\delta w}=(a-y)\delta'(z)x$$,$$\frac{\delta J}{\delta b}=(a-y)\delta'(z)$$ - -其中,$z$表示神经元的输入,$\delta$表示激活函数。权值$w$和偏置$b$的梯度跟激活函数的梯度成正比,激活函数的梯度越大,权值$w$和偏置$b$的大小调整得越快,训练收敛得就越快。 +​ 其中,$J$表示代价函数,$x$表示样本,$y$示实际值,$a$表示输出值,$n$表示样本的总数。使用一个样本为例简单说明,此时二次代价函数为: +$$ +J = \frac{(y-a)^2}{2} +$$ +​ 假如使用梯度下降法(Gradient descent)来调整权值参数的大小,权值$w$和偏置$b$的梯度推导如下: +$$ +\frac{\delta J}{\delta b}=(a-y)\delta'(z) +$$ +其中,$z​$表示神经元的输入,$\theta​$表示激活函数。权值$w​$和偏置$b​$的梯度跟激活函数的梯度成正比,激活函数的梯度越大,权值$w​$和偏置$b​$的大小调整得越快,训练收敛得就越快。 *注*:神经网络常用的激活函数为sigmoid函数,该函数的曲线如下所示: ![](./img/ch2/2.18/1.jpg) -如图所示,对0.88和0.98两个点进行比较: -假设目标是收敛到1.0。0.88离目标1.0比较远,梯度比较大,权值调整比较大。0.98离目标1.0比较近,梯度比较小,权值调整比较小。调整方案合理。 -假如目标是收敛到0。0.88离开目标0比较近,梯度比较大,权值调整比较大。0.98离目标0比较远,梯度比较小,权值调整比较小。调整方案不合理。 -原因:使用sigmoid情况下,初始的代价(误差)越大,导致训练越慢。 +​ 假设目标是收敛到1.0。0.82离目标比较远,梯度比较大,权值调整比较大。0.98离目标比较近,梯度比较小,权值调整比较小。调整方案合理。 +​ 假如目标是收敛到0。0.82目标比较近,梯度比较大,权值调整比较大。0.98离目标比较远,梯度比较小,权值调整比较小。调整方案不合理。 +​ 原因:初始的代价(误差)越大,导致训练越慢。 2. **交叉熵代价函数(cross-entropy)**: 交叉熵代价函数: $$ -J = -\frac{1}{n}\sum_x[y\ln a + (1-y)\ln{(1-a)}] +J = \frac{1}{n}\sum_x[y\ln a + (1-y)\ln{(1-a)}] $$ 其中,$J$表示代价函数,$x$表示样本,$y$表示实际值,$a$表示输出值,$n$表示样本的总数。 -权值$w$和偏置$b$的梯度推导如下: - + 权值$w$和偏置$b​$的梯度推导如下: $$ -\frac{\partial J}{\partial w_j}=\frac{1}{n}\sum_{x}x_j(\sigma{(z)}-y)\;, -\frac{\partial J}{\partial b}=\frac{1}{n}\sum_{x}(\sigma{(z)}-y) +\frac{\delta J}{\delta w_j}=\frac{1}{n}\sum_{x}(\delta{(a)}-y)\;, +\frac{\delta J}{\delta b}=\frac{1}{n}\sum_{x}(\delta{(z)}-y) $$ 当误差越大时,梯度就越大,权值$w$和偏置$b$调整就越快,训练的速度也就越快。 **二次代价函数适合输出神经元是线性的情况,交叉熵代价函数适合输出神经元是S型函数的情况。** -3. **对数似然代价函数(log-likelihood cost)**: -对数似然函数常用来作为softmax回归的代价函数。深度学习中普遍的做法是将softmax作为最后一层,此时常用的代价函数是对数似然代价函数。 - 对数似然代价函数与softmax的组合和交叉熵与sigmoid函数的组合非常相似。对数似然代价函数在二分类时可以化简为交叉熵代价函数的形式。 +3. **对数释然代价函数(log-likelihood cost)**: + 对数释然函数常用来作为softmax回归的代价函数。深度学习中普遍的做法是将softmax作为最后一层,此时常用的代价函数是对数释然代价函数。 + 对数似然代价函数与softmax的组合和交叉熵与sigmoid函数的组合非常相似。对数释然代价函数在二分类时可以化简为交叉熵代价函数的形式。 在tensorflow中: - 与sigmoid搭配使用的交叉熵函数:`tf.nn.sigmoid_cross_entropy_with_logits()`。 - 与softmax搭配使用的交叉熵函数:`tf.nn.softmax_cross_entropy_with_logits()`。 + 与sigmoid搭配使用的交叉熵函数:`tf.nn.sigmoid_cross_entropy_with_logits()`。 + 与softmax搭配使用的交叉熵函数:`tf.nn.softmax_cross_entropy_with_logits()`。 ### 2.10.5 为什么用交叉熵代替二次代价函数 1. **为什么不用二次方代价函数** -由2.18节可知,权值$w$和偏置$b$的偏导数为$\frac{\delta J}{\delta w}=(a-y)\delta'(z)x$,$\frac{\delta J}{\delta b}=(a-y)\delta'(z)$, 偏导数受激活函数的导数影响,sigmoid函数导数在输出接近0和1时非常小,会导致一些实例在刚开始训练时学习得非常慢。 +由上一节可知,权值$w$和偏置$b$的偏导数为$\frac{\delta J}{\delta w}=(a-y)\delta'(z)x$,$\frac{\delta J}{\delta b}=(a-y)\delta'(z)$, 偏导数受激活函数的导数影响,sigmoid函数导数在输出接近0和1时非常小,会导致一些实例在刚开始训练时学习得非常慢。 2. **为什么要用交叉熵** 交叉熵函数权值$w$和偏置$b$的梯度推导为: @@ -350,16 +367,16 @@ $$ ### 2.11.1 什么是损失函数? -损失函数(Loss function)又叫做误差函数,用来衡量算法的运行情况,估量模型的预测值 与真实值 的不一致程度,是一个非负实值函数,通常使用 来表示,损失函数越小,模型的鲁棒性就越好。 +​ 损失函数(Loss function)又叫做误差函数,用来衡量算法的运行情况,估量模型的预测值 与真实值 的不一致程度,是一个非负实值函数,通常使用 来表示,损失函数越小,模型的鲁棒性就越好。 损失函数是经验风险函数的核心部分,也是结构风险函数重要组成部分。 ### 2.11.2 常见的损失函数 -机器学习通过对算法中的目标函数进行不断求解优化,得到最终想要的结果。分类和回归问题中,通常使用损失函数或代价函数作为目标函数。 -损失函数用来评价预测值和真实值不一样的程度。通常损失函数越好,模型的性能也越好。 -损失函数可分为经验风险损失函数和结构风险损失函数。经验风险损失函数指预测结果和实际结果的差别,结构风险损失函数是在经验风险损失函数上加上正则项。 -下面介绍常用的损失函数: +​ 机器学习通过对算法中的目标函数进行不断求解优化,得到最终想要的结果。分类和回归问题中,通常使用损失函数或代价函数作为目标函数。 +​ 损失函数用来评价预测值和真实值不一样的程度。通常损失函数越好,模型的性能也越好。 +​ 损失函数可分为经验风险损失函数和结构风险损失函数。经验风险损失函数指预测结果和实际结果的差别,结构风险损失函数是在经验风险损失函数上加上正则项。 +​ 下面介绍常用的损失函数: -1. 0-1损失函数 +1. **0-1损失函数** 如果预测值和目标值相等,值为0,如果不相等,值为1. $$ @@ -380,14 +397,14 @@ L(Y, f(x)) = \end{cases} $$ -2. 绝对值损失函数 +2. **绝对值损失函数** 和0-1损失函数相似,绝对值损失函数表示为: $$ L(Y, f(x)) = |Y-f(x)|​ $$ -3. 平方损失函数 +3. **平方损失函数** $$ L(Y, f(x)) = \sum_N{(Y-f(x))}^2 @@ -395,15 +412,15 @@ $$ 这点可从最小二乘法和欧几里得距离角度理解。最小二乘法的原理是,最优拟合曲线应该使所有点到回归直线的距离和最小。 -4. log对数损失函数 +4. **log对数损失函数** $$ L(Y, P(Y|X)) = -\log{P(Y|X)} $$ -常见的逻辑回归使用的就是对数损失函数,有很多人认为逻辑回归的损失函数式平方损失,其实不然。逻辑回归它假设样本服从伯努利分布,进而求得满足该分布的似然函数,接着取对数求极值等。逻辑回归推导出的经验风险函数是最小化负的似然函数,从损失函数的角度看,就是log损失函数。 +​ 常见的逻辑回归使用的就是对数损失函数,有很多人认为逻辑回归的损失函数式平方损失,其实不然。逻辑回归它假设样本服从伯努利分布,进而求得满足该分布的似然函数,接着取对数求极值等。逻辑回归推导出的经验风险函数是最小化负的似然函数,从损失函数的角度看,就是log损失函数。 -5. 指数损失函数 +5. **指数损失函数** 指数损失函数的标准形式为: $$ @@ -412,7 +429,7 @@ $$ 例如AdaBoost就是以指数损失函数为损失函数。 -6. Hinge损失函数 +6. **Hinge损失函数** Hinge损失函数的标准形式如下: $$ @@ -437,32 +454,88 @@ $$ ### 2.11.3 逻辑回归为什么使用对数损失函数? 假设逻辑回归模型 -$$y=\frac{1}{1+exp(-(wx+b))}$$ -sigmoid的值域$y \in (-1,1) $, 可以假设它是某种概率,概率分布为 $p(x)$ - -对于已经发生的事件(不同事件之间相互独立)$X=\{X_i\}$,其似然函数为: -$$p(X)=\prod_ip(X_i)$$ -目标为 **最大化似然函数**, 而一连串的概率相乘值会很小, 故取对数(不改变单调性): -$$log(p(X))=log(\prod_ip(X_i))=\sum_ilog(p(X_i))$$ -优化目标等价: -$$\arg \max_{w,b}p(X)=\arg \max_{w,b}\prod_ip(X_i)=\arg \max_{w,b}log(p(X))=\arg \min_{w,b}-log(p(X))$$ -即损失函数: -$$Loss(X)=-log(p(X))=-\sum_ilog(p(X_i))$$ - +$$ +P(y=1|x;\theta)=\frac{1}{1+e^{-\theta^{T}x}} +$$ +假设逻辑回归模型的概率分布是伯努利分布,其概率质量函数为 +$$ +P(X=n)= +\begin{cases} +1-p, n=0\\ + p,n=1 +\end{cases} +$$ +其似然函数为 +$$ +L(\theta)=\prod_{i=1}^{m} +P(y=1|x_i)^{y_i}P(y=0|x_i)^{1-y_i} +$$ +对数似然函数为 +$$ +\ln L(\theta)=\sum_{i=1}^{m}[y_i\ln{P(y=1|x_i)}+(1-y_i)\ln{P(y=0|x_i)}]\\ + =\sum_{i=1}^m[y_i\ln{P(y=1|x_i)}+(1-y_i)\ln(1-P(y=1|x_i))] +$$ +对数函数在单个数据点上的定义为 +$$ +cost(y,p(y|x))=-y\ln{p(y|x)-(1-y)\ln(1-p(y|x))} +$$ +则全局样本损失函数为: +$$ +cost(y,p(y|x)) = -\sum_{i=1}^m[y_i\ln p(y_i|x_i)-(1-y_i)\ln(1-p(y_i|x_i))] +$$ 由此可看出,对数损失函数与极大似然估计的对数似然函数本质上是相同的。所以逻辑回归直接采用对数损失函数。 ### 2.11.4 对数损失函数是如何度量损失的? -对于一个样本来说, 得到的概率为$y_{pred}=p(x)$ -而在二分类中它对应的目标概率应该=1(正类)或者=0(负类). - -举正类来说$y_{label}=1$, -它在$y_{pred}=1$时损失应该最小; -它在$y_{pred}=0$时损失应该最大. -正好与$-log(y)$的单调性一致, -也可以有其他的损失函数,保证它在(0,1)区间上的单调递减. +举例: + 高斯分布中,我们需要确定均值和标准差 。 + 如何确定这两个参数?最大似然估计是比较常用的方法。最大似然的目标是找到一些参数值,这些参数值对应的分布可以最大化观测到数据的概率。 + 因为需要计算观测到所有数据的全概率,即所有观测到的数据点的联合概率。现考虑如下简化情况: + +1. 假设观测到每个数据点的概率和其他数据点的概率是独立的。 +2. 取自然对数。 + 假设观测到单个数据点$x_i(i=1,2,...n)​$的概率为: +$$ +P(x_i;\mu,\sigma)=\frac{1}{\sigma \sqrt{2\pi}}\exp + \left( - \frac{(x_i-\mu)^2}{2\sigma^2} \right) +$$ -选择$-log(y)$作为损失的原因,正如2.11.3节中所推导的 等价性. +3. 其联合概率为 + $$ + P(x_1,x_2,...,x_n;\mu,\sigma)=\frac{1}{\sigma \sqrt{2\pi}}\exp + \left( - \frac{(x_1-\mu)^2}{2\sigma^2} \right) \\ \times + \frac{1}{\sigma \sqrt{2\pi}}\exp + \left( - \frac{(x_2-\mu)^2}{2\sigma^2} \right) \times ... \times + \frac{1}{\sigma \sqrt{2\pi}}\exp + \left( - \frac{(x_n-\mu)^2}{2\sigma^2} \right) + $$ + + + 对上式取自然对数,可得: + $$ + \ln(P(x_1,x_2,...x_n;\mu,\sigma))= + \ln \left(\frac{1}{\sigma \sqrt{2\pi}} \right) + - \frac{(x_1-\mu)^2}{2\sigma^2} \\ + + \ln \left( \frac{1}{\sigma \sqrt{2\pi}} \right) + - \frac{(x_2-\mu)^2}{2\sigma^2} +...+ + \ln \left( \frac{1}{\sigma \sqrt{2\pi}} \right) + - \frac{(x_n-\mu)^2}{2\sigma^2} + $$ + 根据对数定律,上式可以化简为: + $$ + \ln(P(x_1,x_2,...x_n;\mu,\sigma))=-n\ln(\sigma)-\frac{n}{2} \ln(2\pi)\\ + -\frac{1}{2\sigma^2}[(x_1-\mu)^2+(x_2-\mu)^2+...+(x_n-\mu)^2] + $$ + 求导: + $$ + \frac{\partial\ln(P(x_1,x_2,...,x_n;\mu,\sigma))}{\partial\mu}= + \frac{1}{\sigma^2}[x_1+x_2+...+x_n] + $$ + 上式左半部分为对数损失函数。损失函数越小越好,因此我们令对数损失函数为0,可得: + $$ + \mu=\frac{x_1+x_2+...+x_n}{n} + $$ + 同理,可计算$\sigma​$。 ## 2.12 梯度下降 @@ -493,107 +566,152 @@ $$Loss(X)=-log(p(X))=-\sum_ilog(p(X_i))$$ > 由上图,假如最开始,我们在一座大山上的某处位置,因为到处都是陌生的,不知道下山的路,所以只能摸索着根据直觉,走一步算一步,在此过程中,每走到一个位置的时候,都会求解当前位置的梯度,沿着梯度的负方向,也就是当前最陡峭的位置向下走一步,然后继续求解当前位置梯度,向这一步所在位置沿着最陡峭最易下山的位置走一步。不断循环求梯度,就这样一步步的走下去,一直走到我们觉得已经到了山脚。当然这样走下去,有可能我们不能走到山脚,而是到了某一个局部的山峰低处。 由此,从上面的解释可以看出,梯度下降不一定能够找到全局的最优解,有可能是一个局部最优解。当然,如果损失函数是凸函数,梯度下降法得到的解就一定是全局最优解。 -核心思想归纳: +**核心思想归纳**: + 1. 初始化参数,随机选取取值范围内的任意数; 2. 迭代操作: - a) 计算当前梯度; - b)修改新的变量; - c)计算朝最陡的下坡方向走一步; - d)判断是否需要终止,如否,返回a); + a)计算当前梯度; +b)修改新的变量; +c)计算朝最陡的下坡方向走一步; +d)判断是否需要终止,如否,返回a); 3. 得到全局最优解或者接近全局最优解。 -### 2.12.4 梯度下降法算法描述? +### 2.12.4 梯度下降法算法描述 1. 确定优化模型的假设函数及损失函数。 -举例,对于线性回归,假设函数为: -TODO -其中,TODO分别为模型参数、每个样本的特征值。 -对于假设函数,损失函数为: -TODO + 举例,对于线性回归,假设函数为: +$$ + h_\theta(x_1,x_2,...,x_n)=\theta_0+\theta_1x_1+...+\theta_nx_n +$$ + 其中,$\theta,x_i(i=1,2,...,n)​$分别为模型参数、每个样本的特征值。 + 对于假设函数,损失函数为: +$$ + J(\theta_0,\theta_1,...,\theta_n)=\frac{1}{2m}\sum^{m}_{j=0}(h_\theta (x^{(j)}_0) + ,(x^{(j)}_1),...,(x^{(j)}_n)-y_j)^2 +$$ + 2. 相关参数初始化。 -主要初始化TODO、算法迭代步长TODO、终止距离TODO。初始化时可以根据经验初始化,即TODO初始化为0,步长TODO初始化为1。当前步长记为TODO。当然,也可随机初始化。 -3. 迭代计算。 + 主要初始化${\theta}_i​$、算法迭代步长${\alpha}​$、终止距离${\zeta}​$。初始化时可以根据经验初始化,即${\theta}​$初始化为0,步长${\alpha}​$初始化为1。当前步长记为${\varphi}_i​$。当然,也可随机初始化。 -1) 计算当前位置时损失函数的梯度,对TODO,其梯度表示为:TODO +3. 迭代计算。 -2) 计算当前位置下降的距离。TODO + 1) 计算当前位置时损失函数的梯度,对${\theta}_i$,其梯度表示为: -3) 判断是否终止。 -确定是否所有TODO梯度下降的距离TODO都小于终止距离TODO,如果都小于TODO,则算法终止,当然的值即为最终结果,否则进入下一步。 -4) 更新所有的TODO,更新后的表达式为:TODO -5) 更新完毕后转入1)。 +$$ +\frac{\partial}{\partial \theta_i}J({\theta}_0,{\theta}_1,...,{\theta}_n) +$$ +​ 2) 计算当前位置下降的距离。 +$$ +{\varphi}_i={\alpha} \frac{\partial}{\partial \theta_i}J({\theta}_0,{\theta}_1,...,{\theta}_n) +$$ +​ 3) 判断是否终止。 +​ 确定是否所有${\theta}_i$梯度下降的距离${\varphi}_i$都小于终止距离${\zeta}$,如果都小于${\zeta}$,则算法终止,当然的值即为最终结果,否则进入下一步。 +​ 4) 更新所有的${\theta}_i$,更新后的表达式为: +$$ +{\theta}_i={\theta}_i-\alpha \frac{\partial}{\partial \theta_i}J({\theta}_0,{\theta}_1,...,{\theta}_n) +$$ +​ 5) 更新完毕后转入1)。 **举例**。以线性回归为例。 假设样本是 -TODO +$$ +(x^{(0)}_1,x^{(0)}_2,...,x^{(0)}_n,y_0),(x^{(1)}_1,x^{(1)}_2,...,x^{(1)}_n,y_1),..., +(x^{(m)}_1,x^{(m)}_2,...,x^{(m)}_n,y_m) +$$ 损失函数为 -TODO -在计算中,TODO的偏导数计算如下: -TODO -令上式 。4)中TODO的更新表达式为: - TODO -由此,可看出,当前位置的梯度方向由所有样本决定,上式中TODO的目的是为了便于理解。 +$$ +J(\theta_0,\theta_1,...,\theta_n)=\frac{1}{2m}\sum^{m}_{j=0}(h_\theta (x^{(j)}_0 + ,x^{(j)}_1,...,x^{(j)}_n)-y_j)^2 +$$ +在计算中,${\theta}_i$ 的偏导数计算如下: +$$ +\frac{\partial}{\partial \theta_i}J({\theta}_0,{\theta}_1,...,{\theta}_n)=\frac{1}{m}\sum^{m}_{j=0}(h_\theta (x^{(j)}_0 + ,x^{(j)}_1,...,x^{(j)}_n)-y_j)x^{(j)}_i +$$ +令上式$x^{(j)}_0=1$ 。4)中 $\theta_i$ 的更新表达式为: +$$ +\theta_i=\theta_i - \alpha \frac{1}{m} \sum^{m}_{j=0}(h_\theta (x^{(j)}_0 + ,x^{(j)}_1,...,x^{(j)}_n)-y_j)x^{(j)}_i +$$ + + +由此,可看出,当前位置的梯度方向由所有样本决定,上式中 $\frac{1}{m}​$、$\alpha \frac{1}{m}​$ 的目的是为了便于理解。 ### 2.12.5 如何对梯度下降法进行调优? 实际使用梯度下降法时,各项参数指标不能一步就达到理想状态,对梯度下降法调优主要体现在以下几个方面: 1. **算法迭代步长$\alpha$选择。** -在算法参数初始化时,有时根据经验将步长 初始化为1。实际取值取决于数据样本。可以从大到小,多取一些值,分别运行算法看迭代效果,如果损失函数在变小,则取值有效。如果取值无效,说明要增大步长。但步长太大,有时会导致迭代速度过快,错过最优解。步长太小,迭代速度慢,算法运行时间长。 + 在算法参数初始化时,有时根据经验将步长初始化为1。实际取值取决于数据样本。可以从大到小,多取一些值,分别运行算法看迭代效果,如果损失函数在变小,则取值有效。如果取值无效,说明要增大步长。但步长太大,有时会导致迭代速度过快,错过最优解。步长太小,迭代速度慢,算法运行时间长。 2. **参数的初始值选择。** -初始值不同,获得的最小值也有可能不同,梯度下降有可能得到的是局部最小值。如果损失函数是凸函数,则一定是最优解。由于有局部最优解的风险,需要多次用不同初始值运行算法,关键损失函数的最小值,选择损失函数最小化的初值。 + 初始值不同,获得的最小值也有可能不同,梯度下降有可能得到的是局部最小值。如果损失函数是凸函数,则一定是最优解。由于有局部最优解的风险,需要多次用不同初始值运行算法,关键损失函数的最小值,选择损失函数最小化的初值。 3. **标准化处理。** -由于样本不同,特征取值范围也不同,导致迭代速度慢。为了减少特征取值的影响,可对特征数据标准化,使新期望为0,新方差为1,可节省算法运行时间。 + 由于样本不同,特征取值范围也不同,导致迭代速度慢。为了减少特征取值的影响,可对特征数据标准化,使新期望为0,新方差为1,可节省算法运行时间。 ### 2.12.7 随机梯度和批量梯度区别? -随机梯度下降和批量梯度下降是两种主要梯度下降法,其目的是增加某些限制来加速运算求解。 -引入随机梯度下降法与mini-batch梯度下降法是为了应对大数据量的计算而实现一种快速的求解。 +​ 随机梯度下降和批量梯度下降是两种主要梯度下降法,其目的是增加某些限制来加速运算求解。 下面通过介绍两种梯度下降法的求解思路,对其进行比较。 假设函数为 -TODO +$$ +h_\theta (x_1,x_2,...,x_3) = \theta_0 + \theta_1 + ... + \theta_n x_n +$$ 损失函数为 -TODO -其中,TODO为样本个数,TODO为参数个数。 +$$ +J(\theta_0, \theta_1, ... , \theta_n) = + \frac{1}{2m} \sum^{m}_{j=0}(h_\theta (x^{(j)}_0 + ,x^{(j)}_1,...,x^{(j)}_n)-y_j)^2 +$$ +其中,$m​$为样本个数,$j​$为参数个数。 1、 **批量梯度下降的求解思路如下:** -a) 得到每个TODO对应的梯度: -TODO - -b) 由于是求最小化风险函数,所以按每个参数TODO的梯度负方向更新TODO: -TODO - -c) 从上式可以注意到,它得到的虽然是一个全局最优解,但每迭代一步,都要用到训练集所有的数据,如果样本数据 很大,这种方法迭代速度就很慢。 +a) 得到每个$ \theta ​$对应的梯度: +$$ +\frac{\partial}{\partial \theta_i}J({\theta}_0,{\theta}_1,...,{\theta}_n)=\frac{1}{m}\sum^{m}_{j=0}(h_\theta (x^{(j)}_0 + ,x^{(j)}_1,...,x^{(j)}_n)-y_j)x^{(j)}_i +$$ +b) 由于是求最小化风险函数,所以按每个参数 $ \theta ​$ 的梯度负方向更新 $ \theta_i ​$ : +$$ +\theta_i=\theta_i - \frac{1}{m} \sum^{m}_{j=0}(h_\theta (x^{(j)}_0 + ,x^{(j)}_1,...,x^{(j)}_n)-y_j)x^{(j)}_i +$$ +c) 从上式可以注意到,它得到的虽然是一个全局最优解,但每迭代一步,都要用到训练集所有的数据,如果样本数据很大,这种方法迭代速度就很慢。 相比而言,随机梯度下降可避免这种问题。 2、**随机梯度下降的求解思路如下:** a) 相比批量梯度下降对应所有的训练样本,随机梯度下降法中损失函数对应的是训练集中每个样本的粒度。 损失函数可以写成如下这种形式, - TODO - -b)对每个参数TODO按梯度方向更新 : - TODO - +$$ +J(\theta_0, \theta_1, ... , \theta_n) = + \frac{1}{m} \sum^{m}_{j=0}(y_i - h_\theta (x^{(j)}_0 + ,x^{(j)}_1,...,x^{(j)}_n))^2 = + \frac{1}{m} \sum^{m}_{j=0} cost(\theta,(x^j,y^j)) +$$ +b)对每个参数 $ \theta​$ 按梯度方向更新 $ \theta​$: +$$ +\theta_i = \theta_i + (y_j - h_\theta (x^{(j)}_0, x^{(j)}_1, ... ,x^{(j)}_n)) +$$ c) 随机梯度下降是通过每个样本来迭代更新一次。 随机梯度下降伴随的一个问题是噪音较批量梯度下降要多,使得随机梯度下降并不是每次迭代都向着整体最优化方向。 **小结:** 随机梯度下降法、批量梯度下降法相对来说都比较极端,简单对比如下: -批量梯度下降: -a)采用所有数据来梯度下降。 -b) 批量梯度下降法在样本量很大的时候,训练速度慢。 -随机梯度下降: -a) 随机梯度下降用一个样本来梯度下降。 -b) 训练速度很快。 +| 方法 | 特点 | +| :----------: | :----------------------------------------------------------- | +| 批量梯度下降 | a)采用所有数据来梯度下降。
b) 批量梯度下降法在样本量很大的时候,训练速度慢。 | +| 随机梯度下降 | a) 随机梯度下降用一个样本来梯度下降。
b) 训练速度很快。 c) 随机梯度下降法仅仅用一个样本决定梯度方向,导致解有可能不是最优。 -d) 收敛速度来说,随机梯度下降法一次迭代一个样本,导致迭代方向变化很大,不能很快的收敛到局部最优解。 +d) 收敛速度来说,随机梯度下降法一次迭代一个样本,导致迭代方向变化很大,不能很快的收敛到局部最优解。 | 下面介绍能结合两种方法优点的小批量梯度下降法。 3、 **小批量(mini-batch)梯度下降的求解思路如下** 对于总数为$m$个样本的数据,根据样本的数据,选取其中的$n(1< n< m)$个子样本来迭代。其参数$\theta$按梯度方向更新$\theta_i$公式如下: -TODO +$$ +\theta_i = \theta_i - \alpha \sum^{t+n-1}_{j=t} + ( h_\theta (x^{(j)}_{0}, x^{(j)}_{1}, ... , x^{(j)}_{n} ) - y_j ) x^{j}_{i} +$$ ### 2.12.8 各种梯度下降法性能比较 -下表简单对比随机梯度下降(SGD)、批量梯度下降(BGD)、小批量梯度下降(mini-batch GD)、和online GD的区别,主要区别在于如何选取训练数据: +下表简单对比随机梯度下降(SGD)、批量梯度下降(BGD)、小批量梯度下降(mini-batch GD)、和online GD的区别: |BGD|SGD|GD|Mini-batch GD|Online GD| |:-:|:-:|:-:|:-:|:-:|:-:| @@ -605,26 +723,28 @@ TODO BGD、SGD、Mini-batch GD,前面均已讨论过,这里介绍一下Online GD。 -Online GD于mini-batch GD/SGD的区别在于,所有训练数据只用一次,然后丢弃。这样做的优点在于可预测最终模型的变化趋势。 +​ Online GD于mini-batch GD/SGD的区别在于,所有训练数据只用一次,然后丢弃。这样做的优点在于可预测最终模型的变化趋势。 -Online GD在互联网领域用的较多,比如搜索广告的点击率(CTR)预估模型,网民的点击行为会随着时间改变。用普通的BGD算法(每天更新一次)一方面耗时较长(需要对所有历史数据重新训练);另一方面,无法及时反馈用户的点击行为迁移。而Online GD算法可以实时的依据网民的点击行为进行迁移。 +​ Online GD在互联网领域用的较多,比如搜索广告的点击率(CTR)预估模型,网民的点击行为会随着时间改变。用普通的BGD算法(每天更新一次)一方面耗时较长(需要对所有历史数据重新训练);另一方面,无法及时反馈用户的点击行为迁移。而Online GD算法可以实时的依据网民的点击行为进行迁移。 ## 2.13 计算图的导数计算图解? ​ 计算图导数计算是反向传播,利用链式法则和隐式函数求导。 -​ 假设TODO在点TODO处偏导连续,TODO是关于TODO的函数,在TODO点可导,求TODO在TODO点的导数。 +​ 假设 $z = f(u,v)$ 在点 $(u,v)$ 处偏导连续,$(u,v)$是关于 $t$ 的函数,在 $t$ 点可导,求 $z$ 在 $t$ 点的导数。 根据链式法则有 -TODO +$$ +\frac{dz}{dt}=\frac{\partial z}{\partial u}.\frac{du}{dt}+\frac{\partial z}{\partial v} + .\frac{dv}{dt} +$$ ​ 为了便于理解,下面举例说明。 -假设$f(x)$是关于a,b,c的函数。链式求导法则如下: - +假设$f(x)​$是关于a,b,c的函数。链式求导法则如下: $$ \frac{dJ}{du}=\frac{dJ}{dv}\frac{dv}{du},\frac{dJ}{db}=\frac{dJ}{du}\frac{du}{db},\frac{dJ}{da}=\frac{dJ}{du}\frac{du}{da} $$ -​链式法则用文字描述:“由两个函数凑起来的复合函数,其导数等于里边函数代入外边函数的值之导数,乘以里边函数的导数。 +​ 链式法则用文字描述:“由两个函数凑起来的复合函数,其导数等于里边函数代入外边函数的值之导数,乘以里边函数的导数。 例: @@ -635,17 +755,15 @@ $$ 则 $$ -{f[g(x)]}'=2[g(x)]*g'(x)=2[2x+1]*2=8x+1 +{f[g(x)]}'=2[g(x)] \times g'(x)=2[2x+1] \times 2=8x+1 $$ ## 2.14 线性判别分析(LDA) -### 2.14.1 线性判别分析(LDA)思想总结 - -线性判别分析(Linear Discriminant Analysis,LDA)是一种经典的降维方法。 +### 2.14.1 LDA思想总结 -和PCA不考虑样本类别输出的无监督降维技术不同,LDA是一种监督学习的降维技术,数据集的每个样本有类别输出。 +​ 线性判别分析(Linear Discriminant Analysis,LDA)是一种经典的降维方法。和PCA不考虑样本类别输出的无监督降维技术不同,LDA是一种监督学习的降维技术,数据集的每个样本有类别输出。 LDA分类思想简单总结如下: 1. 多维空间中,数据处理分类问题较为复杂,LDA算法将多维空间中的数据投影到一条直线上,将d维数据转化成1维数据进行处理。 @@ -654,78 +772,89 @@ LDA分类思想简单总结如下: 如果用一句话概括LDA思想,即“投影后类内方差最小,类间方差最大”。 ### 2.14.2 图解LDA核心思想 -假设有红、蓝两类数据,这些数据特征均为二维,如下图所示。我们的目标是将这些数据投影到一维,让每一类相近的数据的投影点尽可能接近,不同类别数据尽可能远,即图中红色和蓝色数据中心之间的距离尽可能大。 +​ 假设有红、蓝两类数据,这些数据特征均为二维,如下图所示。我们的目标是将这些数据投影到一维,让每一类相近的数据的投影点尽可能接近,不同类别数据尽可能远,即图中红色和蓝色数据中心之间的距离尽可能大。 ![](./img/ch2/2.29/1.png) 左图和右图是两种不同的投影方式。 -左图思路:让不同类别的平均点距离最远的投影方式。 +​ 左图思路:让不同类别的平均点距离最远的投影方式。 -右图思路:让同类别的数据挨得最近的投影方式。 +​ 右图思路:让同类别的数据挨得最近的投影方式。 -从上图直观看出,右图红色数据和蓝色数据在各自的区域来说相对集中,根据数据分布直方图也可看出,所以右图的投影效果好于左图,左图中间直方图部分有明显交集。 +​ 从上图直观看出,右图红色数据和蓝色数据在各自的区域来说相对集中,根据数据分布直方图也可看出,所以右图的投影效果好于左图,左图中间直方图部分有明显交集。 -以上例子是基于数据是二维的,分类后的投影是一条直线。如果原始数据是多维的,则投影后的分类面是一低维的超平面。 +​ 以上例子是基于数据是二维的,分类后的投影是一条直线。如果原始数据是多维的,则投影后的分类面是一低维的超平面。 ### 2.14.3 二类LDA算法原理? -输入:数据集TODO,其中样本TODO是n维向量,TODO,TODO降维后的目标维度TODO。定义 - -TODO为第TODO类样本个数; - -TODO为第TODO类样本的集合; - -TODO为第TODO类样本的均值向量; +​ 输入:数据集 $D=\{(x_1,y_1),(x_2,y_2),...,(x_m,y_m)\}​$,其中样本 $x_i ​$ 是n维向量,$y_i \epsilon \{C_1, C_2, ..., C_k\}​$,降维后的目标维度 $d​$。定义 -TODO为第TODO类样本的协方差矩阵。 +​ $N_j(j=0,1)$ 为第 $j$ 类样本个数; -其中TODO,TODO。 +​ $X_j(j=0,1)$ 为第 $j$ 类样本的集合; -假设投影直线是向量TODO,对任意样本TODO,它在直线TODO上的投影为TODO,两个类别的中心点TODO在直线TODO的投影分别为TODO、TODO。 +​ $u_j(j=0,1)​$ 为第 $j​$ 类样本的均值向量; -LDA的目标是让两类别的数据中心间的距离TODO尽量大,与此同时,希望同类样本投影点的协方差TODO、TODO尽量小,最小化TODO。 -定义 -类内散度矩阵TODO +​ $\sum_j(j=0,1)$ 为第 $j$ 类样本的协方差矩阵。 -类间散度矩阵TODO +其中 +$$ +u_j = \frac{1}{N_j} \sum_{x\epsilon X_j}x(j=0,1), +\sum_j = \sum_{x\epsilon X_j}(x-u_j)(x-u_j)^T(j=0,1) +$$ +​ 假设投影直线是向量 $w$,对任意样本 $x_i$,它在直线 $w$上的投影为 $w^tx_i$,两个类别的中心点 $u_0$, $u_1 $在直线 $w$ 的投影分别为 $w^Tu_0$ 、$w^Tu_1$。 -据上分析,优化目标为TODO +​ LDA的目标是让两类别的数据中心间的距离 $\| w^Tu_0 - w^Tu_1 \|^2_2$ 尽量大,与此同时,希望同类样本投影点的协方差$w^T \sum_0 w$、$w^T \sum_1 w$ 尽量小,最小化 $w^T \sum_0 w - w^T \sum_1 w​$ 。 +​ 定义 +​ 类内散度矩阵 +$$ +S_w = \sum_0 + \sum_1 = + \sum_{x\epsilon X_0}(x-u_0)(x-u_0)^T + + \sum_{x\epsilon X_1}(x-u_1)(x-u_1)^T +$$ +​ 类间散度矩阵 $S_b = (u_0 - u_1)(u_0 - u_1)^T$ -根据广义瑞利商的性质,矩阵TODO的最大特征值为TODO的最大值,矩阵TODO的最大特征值对应的特征向量即为TODO。 +​ 据上分析,优化目标为 +$$ +\arg \max J(w) = \frac{\| w^Tu_0 - w^Tu_1 \|^2_2}{w^T \sum_0w + w^T \sum_1w} = +\frac{w^T(u_0-u_1)(u_0-u_1)^Tw}{w^T(\sum_0 + \sum_1)w} = +\frac{w^TS_bw}{w^TS_ww} +$$ +​ 根据广义瑞利商的性质,矩阵 $S^{-1}_{w} S_b$ 的最大特征值为 $j(w)$ 的最大值,矩阵 $S^{-1}_{w} S_b$ 的最大特征值对应的特征向量即为 $w​$。 ### 2.14.4 LDA算法流程总结? LDA算法降维流程如下: -输入:数据集TODO,其中样本TODO是n维向量,TODO,降维后的目标维度TODO。 +​ 输入:数据集 $D = \{ (x_1,y_1),(x_2,y_2), ... ,(x_m,y_m) \}$,其中样本 $x_i $ 是n维向量,$y_i \epsilon \{C_1, C_2, ..., C_k\}$,降维后的目标维度 $d$ 。 -输出:降维后的数据集TODO。 +​ 输出:降维后的数据集 $\overline{D} $ 。 步骤: -1. 计算类内散度矩阵 。 -2. 计算类间散度矩阵 。 -3. 计算矩阵 。 -4. 计算矩阵 的最大的d个特征值。 -5. 计算d个特征值对应的d个特征向量,记投影矩阵为 。 -6. 转化样本集的每个样本,得到新样本 。 -7. 输出新样本集 +1. 计算类内散度矩阵 $S_w$。 +2. 计算类间散度矩阵 $S_b​$ 。 +3. 计算矩阵 $S^{-1}_wS_b​$ 。 +4. 计算矩阵 $S^{-1}_wS_b$ 的最大的 d 个特征值。 +5. 计算 d 个特征值对应的 d 个特征向量,记投影矩阵为 W 。 +6. 转化样本集的每个样本,得到新样本 $P_i = W^Tx_i​$ 。 +7. 输出新样本集 $\overline{D} = \{ (p_1,y_1),(p_2,y_2),...,(p_m,y_m) \}​$ ### 2.14.5 LDA和PCA区别? |异同点|LDA|PCA| |:-:|:-|:-| -|相同点|1. 两者均可以对数据进行降维;2. 两者在降维时均使用了矩阵特征分解的思想;3. 两者都假设数据符合高斯分布;| -|不同点|有监督的降维方法|无监督的降维方法| -||降维最多降到k-1维|降维多少没有限制| -||可以用于降维,还可以用于分类|只用于降维| -||选择分类性能最好的投影方向|选择样本点投影具有最大方差的方向| -||更明确,更能反映样本间差异|目的较为模糊| +|相同点|1. 两者均可以对数据进行降维;
2. 两者在降维时均使用了矩阵特征分解的思想;
3. 两者都假设数据符合高斯分布;|| +|不同点|有监督的降维方法;|无监督的降维方法;| +||降维最多降到k-1维;|降维多少没有限制;| +||可以用于降维,还可以用于分类;|只用于降维;| +||选择分类性能最好的投影方向;|选择样本点投影具有最大方差的方向;| +||更明确,更能反映样本间差异;|目的较为模糊;| ### 2.14.6 LDA优缺点? |优缺点|简要说明| |:-:|:-| -|优点|1. 可以使用类别的先验知识;2. 以标签,类别衡量差异性的有监督降维方式,相对于PCA的模糊性,其目的更明确,更能反映样本间的差异;| -|缺点|1. LDA不适合对非高斯分布样本进行降维;2. LDA降维最多降到k-1维;3. LDA在样本分类信息依赖方差而不是均值时,降维效果不好;4. LDA可能过度拟合数据。| +|优点|1. 可以使用类别的先验知识;
2. 以标签、类别衡量差异性的有监督降维方式,相对于PCA的模糊性,其目的更明确,更能反映样本间的差异;| +|缺点|1. LDA不适合对非高斯分布样本进行降维;
2. LDA降维最多降到k-1维;
3. LDA在样本分类信息依赖方差而不是均值时,降维效果不好;
4. LDA可能过度拟合数据。| ## 2.15 主成分分析(PCA) @@ -742,9 +871,9 @@ LDA算法降维流程如下: 7. 之所以对角化,因为对角化之后非对角上的元素都是0,达到去噪声的目的。对角化后的协方差矩阵,对角线上较小的新方差对应的就是那些该去掉的维度。所以我们只取那些含有较大能量(特征值)的维度,其余的就舍掉,即去冗余。 ### 2.15.2 图解PCA核心思想 -PCA可解决训练数据中存在数据特征过多或特征累赘的问题。核心思想是将m维特征映射到n维(n < m),这n维形成主元,是重构出来最能代表原始数据的正交特征。 +​ PCA可解决训练数据中存在数据特征过多或特征累赘的问题。核心思想是将m维特征映射到n维(n < m),这n维形成主元,是重构出来最能代表原始数据的正交特征。 -假设数据集是m个n维,$(x^{(1)}, x^{(2)}, \cdots, x^{(m)})$。如果n=2,需要降维到$n'=1$,现在想找到某一维度方向代表这两个维度的数据。下图有$u_1, u_2$两个向量方向,但是哪个向量才是我们所想要的,可以更好代表原始数据集的呢? +​ 假设数据集是m个n维,$(x^{(1)}, x^{(2)}, \cdots, x^{(m)})$。如果n=2,需要降维到$n'=1$,现在想找到某一维度方向代表这两个维度的数据。下图有$u_1, u_2$两个向量方向,但是哪个向量才是我们所想要的,可以更好代表原始数据集的呢? ![](./img/ch2/2.34/1.png) @@ -759,38 +888,58 @@ PCA可解决训练数据中存在数据特征过多或特征累赘的问题。 ### 2.15.3 PCA算法推理 下面以基于最小投影距离为评价指标推理: -假设数据集是m个n维,TODO,且数据进行了中心化。经过投影变换得到新坐标为TODO,其中TODO是标准正交基,即TODO,TODO。经过降维后,新坐标为TODO,其中TODO是降维后的目标维数。样本点TODO在新坐标系下的投影为TODO,其中TODO是TODO在低维坐标系里第j维的坐标。如果用TODO去恢复TODO,则得到的恢复数据为TODO,其中TODO为标准正交基组成的矩阵。 +​ 假设数据集是m个n维,$(x^{(1)}, x^{(2)},...,x^{(m)})$,且数据进行了中心化。经过投影变换得到新坐标为 ${w_1,w_2,...,w_n}$,其中 $w$ 是标准正交基,即 $\| w \|_2 = 1$,$w^T_iw_j = 0$。 -考虑到整个样本集,样本点到这个超平面的距离足够近,目标变为最小化TODO。对此式进行推理,可得: -TODO +​ 经过降维后,新坐标为 $\{ w_1,2_2,...,w_n \}$,其中 $n'$ 是降维后的目标维数。样本点 $x^{(i)}$ 在新坐标系下的投影为 $z^{(i)} = \left(z^{(i)}_1, z^{(i)}_2, ..., z^{(i)}_{n'} \right)$,其中 $z^{(i)}_j = w^T_j x^{(i)}$ 是 $x^{(i)} ​$ 在低维坐标系里第 j 维的坐标。 -在推导过程中,分别用到了TODO,矩阵转置公式TODO,TODO,TODO以及矩阵的迹,最后两步是将代数和转为矩阵形式。 -由于TODO的每一个向量TODO是标准正交基,TODO是数据集的协方差矩阵,TODO是一个常量。最小化TODO又可等价于 +​ 如果用 $z^{(i)} $ 去恢复 $x^{(i)} $ ,则得到的恢复数据为 $\widehat{x}^{(i)} = \sum^{n'}_{j=1} x^{(i)}_j w_j = Wz^{(i)}$,其中 $W$为标准正交基组成的矩阵。 -TODO +​ 考虑到整个样本集,样本点到这个超平面的距离足够近,目标变为最小化 $\sum^m_{i=1} \| \hat{x}^{(i)} - x^{(i)} \|^2_2$ 。对此式进行推理,可得: +$$ +\sum^m_{i=1} \| \hat{x}^{(i)} - x^{(i)} \|^2_2 = + \sum^m_{i=1} \| Wz^{(i)} - x^{(i)} \|^2_2 \\ + = \sum^m_{i=1} \left( Wz^{(i)} \right)^T \left( Wz^{(i)} \right) + - 2\sum^m_{i=1} \left( Wz^{(i)} \right)^T x^{(i)} + + \sum^m_{i=1} \left( x^{(i)} \right)^T x^{(i)} \\ + = \sum^m_{i=1} \left( z^{(i)} \right)^T \left( z^{(i)} \right) + - 2\sum^m_{i=1} \left( z^{(i)} \right)^T x^{(i)} + + \sum^m_{i=1} \left( x^{(i)} \right)^T x^{(i)} \\ + = - \sum^m_{i=1} \left( z^{(i)} \right)^T \left( z^{(i)} \right) + + \sum^m_{i=1} \left( x^{(i)} \right)^T x^{(i)} \\ + = -tr \left( W^T \left( \sum^m_{i=1} x^{(i)} \left( x^{(i)} \right)^T \right)W \right) + + \sum^m_{i=1} \left( x^{(i)} \right)^T x^{(i)} \\ + = -tr \left( W^TXX^TW \right) + + \sum^m_{i=1} \left( x^{(i)} \right)^T x^{(i)} +$$ +​ 在推导过程中,分别用到了 $\overline{x}^{(i)} = Wz^{(i)}$ ,矩阵转置公式 $(AB)^T = B^TA^T$,$W^TW = I$,$z^{(i)} = W^Tx^{(i)}$ 以及矩阵的迹,最后两步是将代数和转为矩阵形式。 +​ 由于 $W$ 的每一个向量 $w_j$ 是标准正交基,$\sum^m_{i=1} x^{(i)} \left( x^{(i)} \right)^T$ 是数据集的协方差矩阵,$\sum^m_{i=1} \left( x^{(i)} \right)^T x^{(i)} $ 是一个常量。最小化 $\sum^m_{i=1} \| \hat{x}^{(i)} - x^{(i)} \|^2_2$ 又可等价于 +$$ +\underbrace{\arg \min}_W - tr \left( W^TXX^TW \right) s.t.W^TW = I +$$ 利用拉格朗日函数可得到 -TODO - -对TODO求导,可得TODO,也即TODO。 是TODO个特征向量组成的矩阵, 为TODO的特征值。TODO即为我们想要的矩阵。 -对于原始数据,只需要TODO,就可把原始数据集降维到最小投影距离的TODO维数据集。 +$$ +J(W) = -tr(W^TXX^TW) + \lambda(W^TW - I) +$$ +​ 对 $W$ 求导,可得 $-XX^TW + \lambda W = 0 $ ,也即 $ XX^TW = \lambda W $ 。 $ XX^T $ 是 $ n' $ 个特征向量组成的矩阵,$\lambda$ 为$ XX^T $ 的特征值。$W$ 即为我们想要的矩阵。 +​ 对于原始数据,只需要 $z^{(i)} = W^TX^{(i)}$ ,就可把原始数据集降维到最小投影距离的 $n'$ 维数据集。 -基于最大投影方差的推导,这里就不再赘述,有兴趣的同仁可自行查阅资料。 +​ 基于最大投影方差的推导,这里就不再赘述,有兴趣的同仁可自行查阅资料。 ### 2.15.4 PCA算法流程总结 -输入:TODO维样本集TODO,目标降维的维数TODO。 +输入:$n​$ 维样本集 $D = \left( x^{(1)},x^{(2)},...,x^{(m)} \right)​$ ,目标降维的维数 $n'​$ 。 -输出:降维后的新样本集TODO。 +输出:降维后的新样本集 $D' = \left( z^{(1)},z^{(2)},...,z^{(m)} \right)$ 。 主要步骤如下: -1. 对所有的样本进行中心化,TODO。 -2. 计算样本的协方差矩阵TODO。 -3. 对协方差矩阵TODO进行特征值分解。 -4. 取出最大的TODO个特征值对应的特征向量TODO。 -5. 标准化特征向量,得到特征向量矩阵TODO。 -6. 转化样本集中的每个样本TODO。 -7. 得到输出矩阵TODO。 -*注*:在降维时,有时不明确目标维数,而是指定降维到的主成分比重阈值TODO。假设TODO个特征值为TODO,则TODO可从TODO得到。 +1. 对所有的样本进行中心化,$ x^{(i)} = x^{(i)} - \frac{1}{m} \sum^m_{j=1} x^{(j)} $ 。 +2. 计算样本的协方差矩阵 $XX^T​$ 。 +3. 对协方差矩阵 $XX^T$ 进行特征值分解。 +4. 取出最大的 $n' $ 个特征值对应的特征向量 $\{ w_1,w_2,...,w_{n'} \}$ 。 +5. 标准化特征向量,得到特征向量矩阵 $W$ 。 +6. 转化样本集中的每个样本 $z^{(i)} = W^T x^{(i)}$ 。 +7. 得到输出矩阵 $D' = \left( z^{(1)},z^{(2)},...,z^{(n)} \right)​$ 。 +*注*:在降维时,有时不明确目标维数,而是指定降维到的主成分比重阈值 $k(k \epsilon(0,1])​$ 。假设 $n​$ 个特征值为 $\lambda_1 \geq \lambda_2 \geq ... \geq \lambda_n​$ ,则 $n'​$ 可从 $\sum^{n'}_{i=1} \lambda_i \geq k \times \sum^n_{i=1} \lambda_i ​$ 得到。 ### 2.15.5 PCA算法主要优缺点 |优缺点|简要说明| @@ -800,7 +949,7 @@ TODO ### 2.15.6 降维的必要性及目的 **降维的必要性**: -1. 多重共线性--预测变量之间相互关联。多重共线性会导致解空间的不稳定,从而可能导致结果的不连贯。 +1. 多重共线性和预测变量之间相互关联。多重共线性会导致解空间的不稳定,从而可能导致结果的不连贯。 2. 高维空间本身具有稀疏性。一维正态分布有68%的值落于正负标准差之间,而在十维空间上只有0.02%。 3. 过多的变量,对查找规律造成冗余麻烦。 4. 仅在变量层面上分析可能会忽略变量之间的潜在联系。例如几个预测变量可能落入仅反映数据某一方面特征的一个组内。 @@ -814,69 +963,87 @@ TODO 6. 降低算法运算开销。 ### 2.15.7 KPCA与PCA的区别? -应用PCA算法的前提是假设存在一个线性的超平面,进而投影。那如果数据不是线性的呢?该怎么办?这时候就需要KPCA,数据集从TODO维映射到线性可分的高维TODO,然后再从TODO维降维到一个低维度TODO。 +​ 应用PCA算法前提是假设存在一个线性超平面,进而投影。那如果数据不是线性的呢?该怎么办?这时候就需要KPCA,数据集从 $n$ 维映射到线性可分的高维 $N >n$,然后再从 $N$ 维降维到一个低维度 $n'(n' 训练误差大,测试误差小 → Bias大 -> -> 训练误差小,测试误差大→ Variance大 → 降VC维 -> -> 训练误差大,测试误差大→ 升VC维 +> ![](./img/ch2/2.16.20.1.png) +> ### 2.16.3 经验误差与泛化误差 -误差(error):一般地,我们把学习器的实际预测输出与样本的真是输出之间的差异称为“误差” -经验误差(empirical error):也叫训练误差(training error)。模型在训练集上的误差。 +经验误差(empirical error):也叫训练误差(training error),模型在训练集上的误差。 泛化误差(generalization error):模型在新样本集(测试集)上的误差称为“泛化误差”。 @@ -884,35 +1051,39 @@ Bias(偏差),Error(误差),和Variance(方差) 根据不同的坐标方式,欠拟合与过拟合图解不同。 1. **横轴为训练样本数量,纵轴为误差** -![](./img/ch2/2.40.3/1.png) +![](./img/ch2/2.16.4.1.jpg) 如上图所示,我们可以直观看出欠拟合和过拟合的区别: -模型欠拟合:在训练集以及测试集上同时具有较高的误差,此时模型的偏差较大; +​ 模型欠拟合:在训练集以及测试集上同时具有较高的误差,此时模型的偏差较大; -模型过拟合:在训练集上具有较低的误差,在测试集上具有较高的误差,此时模型的方差较大。 +​ 模型过拟合:在训练集上具有较低的误差,在测试集上具有较高的误差,此时模型的方差较大。 -模型正常:在训练集以及测试集上,同时具有相对较低的偏差以及方差。 +​ 模型正常:在训练集以及测试集上,同时具有相对较低的偏差以及方差。 2. **横轴为模型复杂程度,纵轴为误差** -![](./img/ch2/2.40.3/2.png) +![](./img/ch2/2.16.4.2.png) -模型欠拟合:模型在点A处,在训练集以及测试集上同时具有较高的误差,此时模型的偏差较大。 +​ 红线为测试集上的Error,蓝线为训练集上的Error -模型过拟合:模型在点C处,在训练集上具有较低的误差,在测试集上具有较高的误差,此时模型的方差较大。 +​ 模型欠拟合:模型在点A处,在训练集以及测试集上同时具有较高的误差,此时模型的偏差较大。 -模型正常:模型复杂程度控制在点B处为最优。 +​ 模型过拟合:模型在点C处,在训练集上具有较低的误差,在测试集上具有较高的误差,此时模型的方差较大。 + +​ 模型正常:模型复杂程度控制在点B处为最优。 3. **横轴为正则项系数,纵轴为误差** -![](./img/ch2/2.40.3/3.png) +![](./img/ch2/2.16.4.3.png) + +​ 红线为测试集上的Error,蓝线为训练集上的Error -模型欠拟合:模型在点C处,在训练集以及测试集上同时具有较高的误差,此时模型的偏差较大。 +​ 模型欠拟合:模型在点C处,在训练集以及测试集上同时具有较高的误差,此时模型的偏差较大。 -模型过拟合:模型在点A处,在训练集上具有较低的误差,在测试集上具有较高的误差,此时模型的方差较大。 它通常发生在模型过于复杂的情况下,如参数过多等,会使得模型的预测性能变弱,并且增加数据的波动性。虽然模型在训练时的效果可以表现的很完美,基本上记住了数据的全部特点,但这种模型在未知数据的表现能力会大减折扣,因为简单的模型泛化能力通常都是很弱的。 +​ 模型过拟合:模型在点A处,在训练集上具有较低的误差,在测试集上具有较高的误差,此时模型的方差较大。 它通常发生在模型过于复杂的情况下,如参数过多等,会使得模型的预测性能变弱,并且增加数据的波动性。虽然模型在训练时的效果可以表现的很完美,基本上记住了数据的全部特点,但这种模型在未知数据的表现能力会大减折扣,因为简单的模型泛化能力通常都是很弱的。 -模型正常:模型复杂程度控制在点B处为最优。 +​ 模型正常:模型复杂程度控制在点B处为最优。 ### 2.16.5 如何解决过拟合与欠拟合? **如何解决欠拟合:** @@ -935,12 +1106,12 @@ Bias(偏差),Error(误差),和Variance(方差) 欠拟合和过拟合这些方法,需要根据实际问题,实际模型,进行选择。 -### 2.16.6 交叉验证的主要作用? -为了得到更为稳健可靠的模型,对模型的泛化误差进行评估,得到模型泛化误差的近似值。当有多个模型可以选择时,我们通常选择“泛化误差”最小的模型。 +### 2.16.6 交叉验证的主要作用 +​ 为了得到更为稳健可靠的模型,对模型的泛化误差进行评估,得到模型泛化误差的近似值。当有多个模型可以选择时,我们通常选择“泛化误差”最小的模型。 -交叉验证的方法有许多种,但是最常用的是:留一交叉验证、k折交叉验证 +​ 交叉验证的方法有许多种,但是最常用的是:留一交叉验证、k折交叉验证。 -### 2.16.7 k折交叉验证? +### 2.16.7 理解k折交叉验证 1. 将含有N个样本的数据集,分成K份,每份含有N/K个样本。选择其中1份作为测试集,另外K-1份作为训练集,测试集就有K种情况。 2. 在每种情况中,用训练集训练模型,用测试集测试模型,计算模型的泛化误差。 3. 交叉验证重复K次,每份验证一次,平均K次的结果或者使用其它结合方式,最终得到一个单一估测,得到模型最终的泛化误差。 @@ -989,161 +1160,179 @@ Bias(偏差),Error(误差),和Variance(方差) 例,在所有实际上有恶性肿瘤的病人中,成功预测有恶性肿瘤的病人的百分比,越高越好。 ### 2.16.11 ROC与AUC -ROC全称是“受试者工作特征”(Receiver Operating Characteristic)。 +​ ROC全称是“受试者工作特征”(Receiver Operating Characteristic)。 -ROC曲线的面积就是AUC(Area Under the Curve)。 +​ ROC曲线的面积就是AUC(Area Under the Curve)。 -AUC用于衡量“二分类问题”机器学习算法性能(泛化能力)。 +​ AUC用于衡量“二分类问题”机器学习算法性能(泛化能力)。 -ROC曲线,通过将连续变量设定出多个不同的临界值,从而计算出一系列真正率和假正率,再以假正率为纵坐标、真正率为横坐标绘制成曲线,曲线下面积越大,诊断准确性越高。在ROC曲线上,最靠近坐标图左上方的点为假正率和真正率均较高的临界值。 +​ ROC曲线,通过将连续变量设定出多个不同的临界值,从而计算出一系列真正率和假正率,再以假正率为纵坐标、真正率为横坐标绘制成曲线,曲线下面积越大,诊断准确性越高。在ROC曲线上,最靠近坐标图左上方的点为假正率和真正率均较高的临界值。 -对于分类器,或者说分类算法,评价指标主要有precision,recall,F-score。下图是一个ROC曲线的示例。 +​ 对于分类器,或者说分类算法,评价指标主要有precision,recall,F-score。下图是一个ROC曲线的示例。 ![](./img/ch2/2.40.10/1.png) ROC曲线的横坐标为false positive rate(FPR),纵坐标为true positive rate(TPR)。其中 -TODO, TODO, -下面着重介绍ROC曲线图中的四个点和一条线。 -第一个点,(0,1),即FPR=0, TPR=1,这意味着FN(false negative)=0,并且FP(false positive)=0。意味着这是一个完美的分类器,它将所有的样本都正确分类。 -第二个点,(1,0),即FPR=1,TPR=0,意味着这是一个最糟糕的分类器,因为它成功避开了所有的正确答案。 -第三个点,(0,0),即FPR=TPR=0,即FP(false positive)=TP(true positive)=0,可以发现该分类器预测所有的样本都为负样本(negative)。 -第四个点,(1,1),即FPR=TPR=1,分类器实际上预测所有的样本都为正样本。 -经过以上分析,ROC曲线越接近左上角,该分类器的性能越好。 - -ROC曲线所覆盖的面积称为AUC(Area Under Curve),可以更直观的判断学习器的性能,AUC越大则性能越好。 +$$ +TPR = \frac{TP}{TP+FN} ,FPR = \frac{FP}{FP+TN}, +$$ + +​ 下面着重介绍ROC曲线图中的四个点和一条线。 +​ 第一个点,(0,1),即FPR=0, TPR=1,这意味着FN(false negative)=0,并且FP(false positive)=0。意味着这是一个完美的分类器,它将所有的样本都正确分类。 +​ 第二个点,(1,0),即FPR=1,TPR=0,意味着这是一个最糟糕的分类器,因为它成功避开了所有的正确答案。 +​ 第三个点,(0,0),即FPR=TPR=0,即FP(false positive)=TP(true positive)=0,可以发现该分类器预测所有的样本都为负样本(negative)。 +​ 第四个点,(1,1),即FPR=TPR=1,分类器实际上预测所有的样本都为正样本。 +​ 经过以上分析,ROC曲线越接近左上角,该分类器的性能越好。 + +​ ROC曲线所覆盖的面积称为AUC(Area Under Curve),可以更直观的判断学习器的性能,AUC越大则性能越好。 ### 2.16.12 如何画ROC曲线? -http://blog.csdn.net/zdy0_2004/article/details/44948511 -下图是一个示例,图中共有20个测试样本,“Class”一栏表示每个测试样本真正的标签(p表示正样本,n表示负样本),“Score”表示每个测试样本属于正样本的概率。 +​ 下图是一个示例,图中共有20个测试样本,“Class”一栏表示每个测试样本真正的标签(p表示正样本,n表示负样本),“Score”表示每个测试样本属于正样本的概率。 步骤: -1、假设已经得出一系列样本被划分为正类的概率,按照大小排序。 -2、从高到低,依次将“Score”值作为阈值threshold,当测试样本属于正样本的概率大于或等于这个threshold时,我们认为它为正样本,否则为负样本。 举例来说,对于图中的第4个样本,其“Score”值为0.6,那么样本1,2,3,4都被认为是正样本,因为它们的“Score”值都大于等于0.6,而其他样本则都认为是负样本。 -3、每次选取一个不同的threshold,得到一组FPR和TPR,即ROC曲线上的一点。以此共得到20组FPR和TPR的值。其中FPR和TPR简单理解如下: -4、根据3)中的每个坐标点点,画图。 + 1、假设已经得出一系列样本被划分为正类的概率,按照大小排序。 + 2、从高到低,依次将“Score”值作为阈值threshold,当测试样本属于正样本的概率大于或等于这个threshold时,我们认为它为正样本,否则为负样本。 举例来说,对于图中的第4个样本,其“Score”值为0.6,那么样本1,2,3,4都被认为是正样本,因为它们的“Score”值都大于等于0.6,而其他样本则都认为是负样本。 + 3、每次选取一个不同的threshold,得到一组FPR和TPR,即ROC曲线上的一点。以此共得到20组FPR和TPR的值。其中FPR和TPR简单理解如下: + 4、根据3)中的每个坐标点点,画图。 ![](./img/ch2/2.40.11/1.jpg) ### 2.16.13 如何计算TPR,FPR? 1、分析数据 -y_true = [0, 0, 1, 1]; -scores = [0.1, 0.4, 0.35, 0.8]; +y_true = [0, 0, 1, 1];scores = [0.1, 0.4, 0.35, 0.8]; 2、列表 -样本 预测属于P的概率(score) 真实类别 -y[0] 0.1 N -y[2] 0.35 P -y[1] 0.4 N -y[3] 0.8 P + +| 样本 | 预测属于P的概率(score) | 真实类别 | +| ---- | ---------------------- | -------- | +| y[0] | 0.1 | N | +| y[1] | 0.35 | P | +| y[2] | 0.4 | N | +| y[3] | 0.8 | P | + 3、将截断点依次取为score值,计算TPR和FPR。 当截断点为0.1时: 说明只要score>=0.1,它的预测类别就是正例。 因为4个样本的score都大于等于0.1,所以,所有样本的预测类别都为P。 -scores = [0.1, 0.4, 0.35, 0.8]; -y_true = [0, 0, 1, 1]; -y_pred = [1, 1, 1, 1]; +scores = [0.1, 0.4, 0.35, 0.8];y_true = [0, 0, 1, 1];y_pred = [1, 1, 1, 1]; 正例与反例信息如下: -真实值 预测值 -​ 正例 反例 -正例 TP=2 FN=0 -反例 FP=2 TN=0 + +| 真实值\预测值 | | | +| ------------- | ---- | ---- | +| | 正例 | 反例 | +| 正例 | TP=2 | FN=0 | +| 反例 | FP=2 | TN=0 | + 由此可得: -TPR = TP/(TP+FN) = 1; -FPR = FP/(TN+FP) = 1; +TPR = TP/(TP+FN) = 1; FPR = FP/(TN+FP) = 1; 当截断点为0.35时: -scores = [0.1, 0.4, 0.35, 0.8] -y_true = [0, 0, 1, 1] -y_pred = [0, 1, 1, 1] +scores = [0.1, 0.4, 0.35, 0.8];y_true = [0, 0, 1, 1];y_pred = [0, 1, 1, 1]; 正例与反例信息如下: -真实值 预测值 -​ 正例 反例 -正例 TP=2 FN=0 -反例 FP=1 TN=1 + +| 真实值\预测值 | | | +| ------------- | ---- | ---- | +| | 正例 | 反例 | +| 正例 | TP=2 | FN=0 | +| 反例 | FP=1 | TN=1 | + 由此可得: -TPR = TP/(TP+FN) = 1; -FPR = FP/(TN+FP) = 0.5; +TPR = TP/(TP+FN) = 1; FPR = FP/(TN+FP) = 0.5; 当截断点为0.4时: -scores = [0.1, 0.4, 0.35, 0.8]; -y_true = [0, 0, 1, 1]; -y_pred = [0, 1, 0, 1]; +scores = [0.1, 0.4, 0.35, 0.8];y_true = [0, 0, 1, 1];y_pred = [0, 1, 0, 1]; 正例与反例信息如下: -真实值 预测值 -​ 正例 反例 -正例 TP=1 FN=1 -反例 FP=1 TN=1 + +| 真实值\预测值 | | | +| ------------- | ---- | ---- | +| | 正例 | 反例 | +| 正例 | TP=1 | FN=1 | +| 反例 | FP=1 | TN=1 | + 由此可得: -TPR = TP/(TP+FN) = 0.5; -FPR = FP/(TN+FP) = 0.5; +TPR = TP/(TP+FN) = 0.5; FPR = FP/(TN+FP) = 0.5; 当截断点为0.8时: -scores = [0.1, 0.4, 0.35, 0.8]; -y_true = [0, 0, 1, 1]; -y_pred = [0, 0, 0, 1]; +scores = [0.1, 0.4, 0.35, 0.8];y_true = [0, 0, 1, 1];y_pred = [0, 0, 0, 1]; + 正例与反例信息如下: -真实值 预测值 -​ 正例 反例 -正例 TP=1 FN=1 -反例 FP=0 TN=2 + +| 真实值\预测值 | | | +| ------------- | ---- | ---- | +| | 正例 | 反例 | +| 正例 | TP=1 | FN=1 | +| 反例 | FP=0 | TN=2 | + 由此可得: -TPR = TP/(TP+FN) = 0.5; -FPR = FP/(TN+FP) = 0; +TPR = TP/(TP+FN) = 0.5; FPR = FP/(TN+FP) = 0; 4、根据TPR、FPR值,以FPR为横轴,TPR为纵轴画图。 ### 2.16.14 如何计算Auc? -a.将坐标点按照横着FPR排序 -b.计算第i个坐标点和第i+1个坐标点的间距 dx; -c.获取第i(或者i+1)个坐标点的纵坐标y; -d.计算面积微元ds = ydx; -e.对面积微元进行累加,得到AUC。 +- 将坐标点按照横着FPR排序 。 +- 计算第$i$个坐标点和第$i+1$个坐标点的间距$dx$ 。 +- 获取第$i$(或者$i+1$)个坐标点的纵坐标y。 +- 计算面积微元$ds=ydx$。 +- 对面积微元进行累加,得到AUC。 ### 2.16.15 为什么使用Roc和Auc评价分类器? -模型有很多评估方法,为什么还要使用ROC和AUC呢? -因为ROC曲线有个很好的特性:当测试集中的正负样本的分布变换的时候,ROC曲线能够保持不变。在实际的数据集中经常会出现样本类不平衡,即正负样本比例差距较大,而且测试数据中的正负样本也可能随着时间变化。 +​ 模型有很多评估方法,为什么还要使用ROC和AUC呢? +​ 因为ROC曲线有个很好的特性:当测试集中的正负样本的分布变换的时候,ROC曲线能够保持不变。在实际的数据集中经常会出现样本类不平衡,即正负样本比例差距较大,而且测试数据中的正负样本也可能随着时间变化。 ### 2.16.17 直观理解AUC -http://blog.csdn.net/cherrylvlei/article/details/52958720 -AUC是ROC右下方的曲线面积。下图展现了三种AUC的值: +​ 下图展现了三种AUC的值: ![](./img/ch2/2.40.15/1.png) -AUC是衡量二分类模型优劣的一种评价指标,表示正例排在负例前面的概率。其他评价指标有精确度、准确率、召回率,而AUC比这三者更为常用。 -因为一般在分类模型中,预测结果都是以概率的形式表现,如果要计算准确率,通常都会手动设置一个阈值来将对应的概率转化成类别,这个阈值也就很大程度上影响了模型准确率的计算。 -我们不妨举一个极端的例子:一个二类分类问题一共10个样本,其中9个样本为正例,1个样本为负例,在全部判正的情况下准确率将高达90%,而这并不是我们希望的结果,尤其是在这个负例样本得分还是最高的情况下,模型的性能本应极差,从准确率上看却适得其反。而AUC能很好描述模型整体性能的高低。这种情况下,模型的AUC值将等于0(当然,通过取反可以解决小于50%的情况,不过这是另一回事了)。 +​ AUC是衡量二分类模型优劣的一种评价指标,表示正例排在负例前面的概率。其他评价指标有精确度、准确率、召回率,而AUC比这三者更为常用。 +​ 一般在分类模型中,预测结果都是以概率的形式表现,如果要计算准确率,通常都会手动设置一个阈值来将对应的概率转化成类别,这个阈值也就很大程度上影响了模型准确率的计算。 +​ 举例: -### 2.16.18 代价敏感错误率与代价曲线 +​ 现在假设有一个训练好的二分类器对10个正负样本(正例5个,负例5个)预测,得分按高到低排序得到的最好预测结果为[1, 1, 1, 1, 1, 0, 0, 0, 0, 0],即5个正例均排在5个负例前面,正例排在负例前面的概率为100%。然后绘制其ROC曲线,由于是10个样本,除开原点我们需要描10个点,如下: -http://blog.csdn.net/cug_lzt/article/details/78295140 +![](./img/ch2/2.16.17-1.png) -不同的错误会产生不同代价。 -以二分法为例,设置代价矩阵如下: +​ 描点方式按照样本预测结果的得分高低从左至右开始遍历。从原点开始,每遇到1便向y轴正方向移动y轴最小步长1个单位,这里是1/5=0.2;每遇到0则向x轴正方向移动x轴最小步长1个单位,这里也是0.2。不难看出,上图的AUC等于1,印证了正例排在负例前面的概率的确为100%。 -![](./img/ch2/2-1.png) +​ 假设预测结果序列为[1, 1, 1, 1, 0, 1, 0, 0, 0, 0]。 -当判断正确的时候,值为0,不正确的时候,分别为$Cost_{01}$和$Cost_{10}$ 。 +![](./img/ch2/2.16.17-2.png) -$Cost_{10}$:表示实际为反例但预测成正例的代价。 +​ 计算上图的AUC为0.96与计算正例与排在负例前面的概率0.8 × 1 + 0.2 × 0.8 = 0.96相等,而左上角阴影部分的面积则是负例排在正例前面的概率0.2 × 0.2 = 0.04。 -$Cost_{01}$:表示实际为正例但是预测为反例的代价。 +​ 假设预测结果序列为[1, 1, 1, 0, 1, 0, 1, 0, 0, 0]。 -**代价敏感错误率**: -$\frac{样本中由模型得到的错误值与代价乘积之和}{总样本}$ +![](./img/ch2/2.16.17-3.png) -其数学表达式为: +​ 计算上图的AUC为0.88与计算正例与排在负例前面的概率0.6 × 1 + 0.2 × 0.8 + 0.2 × 0.6 = 0.88相等,左上角阴影部分的面积是负例排在正例前面的概率0.2 × 0.2 × 3 = 0.12。 -![](./img/ch2/2-2.png) +### 2.16.18 代价敏感错误率与代价曲线 -$D^{+}、D^{-}$分别代表样例集 的正例子集和反例子集。 +不同的错误会产生不同代价。以二分法为例,设置代价矩阵如下: -代价曲线: -在均等代价时,ROC曲线不能直接反应出模型的期望总体代价,而代价曲线可以。 -代价曲线横轴为[0,1]的正例函数代价: +![](./img/ch2/2-1.png) -$P(+)Cost=\frac{p*Cost_{01}}{p*Cost_{01}+(1-p)*Cost_{10}}$ +当判断正确的时候,值为0,不正确的时候,分别为$Cost_{01}​$和$Cost_{10}​$ 。 +$Cost_{10}$:表示实际为反例但预测成正例的代价。 + +$Cost_{01}$:表示实际为正例但是预测为反例的代价。 + +**代价敏感错误率**=样本中由模型得到的错误值与代价乘积之和 / 总样本。 +其数学表达式为: +$$ +E(f;D;cost)=\frac{1}{m}\left( \sum_{x_{i} \in D^{+}}({f(x_i)\neq y_i})\times Cost_{01}+ \sum_{x_{i} \in D^{-}}({f(x_i)\neq y_i})\times Cost_{10}\right) +$$ +$D^{+}、D^{-}​$分别代表样例集 的正例子集和反例子集。 + +**代价曲线**: + 在均等代价时,ROC曲线不能直接反应出模型的期望总体代价,而代价曲线可以。 +代价曲线横轴为[0,1]的正例函数代价: +$$ +P(+)Cost=\frac{p*Cost_{01}}{p*Cost_{01}+(1-p)*Cost_{10}} +$$ 其中p是样本为正例的概率。 代价曲线纵轴维[0,1]的归一化代价: -$Cost_{norm}=\frac{FNR*p*Cost_{01}+FNR*(1-p)*Cost_{10}}{p*Cost_{01}+(1-p)*Cost_{10}}$ - +$$ +Cost_{norm}=\frac{FNR*p*Cost_{01}+FNR*(1-p)*Cost_{10}}{p*Cost_{01}+(1-p)*Cost_{10}} +$$ 其中FPR为假正例率,FNR=1-TPR为假反利率。 @@ -1151,44 +1340,21 @@ $Cost_{norm}=\frac{FNR*p*Cost_{01}+FNR*(1-p)*Cost_{10}}{p*Cost_{01}+(1-p)*Cost_{ 例如,ROC上(TPR,FPR),计算出FNR=1-TPR,在代价平面上绘制一条从(0,FPR)到(1,FNR)的线段,面积则为该条件下期望的总体代价。所有线段下界面积,所有条件下学习器的期望总体代价。 -![](./img/ch2/2-3.png) +![](./img/ch2/2.16.18.1.png) ### 2.16.19 模型有哪些比较检验方法 -http://wenwen.sogou.com/z/q721171854.htm 正确性分析:模型稳定性分析,稳健性分析,收敛性分析,变化趋势分析,极值分析等。 有效性分析:误差分析,参数敏感性分析,模型对比检验等。 有用性分析:关键数据求解,极值点,拐点,变化趋势分析,用数据验证动态模拟等。 高效性分析:时空复杂度分析与现有进行比较等。 -### 2.16.20 偏差与方差 -http://blog.csdn.net/zhihua_oba/article/details/78684257 - -方差公式为: - -$S_{N}^{2}=\frac{1}{N}\sum_{i=1}^{N}(x_{i}-\bar{x})^{2}$ +### 2.16.21 为什么使用标准差? -泛化误差可分解为偏差、方差与噪声之和,即 -generalization error=bias+variance+noise。 +方差公式为:$S^2_{N}=\frac{1}{N}\sum_{i=1}^{N}(x_{i}-\bar{x})^{2}​$ -噪声:描述了在当前任务上任何学习算法所能达到的期望泛化误差的下界,即刻画了学习问题本身的难度。 -假定期望噪声为零,则泛化误差可分解为偏差、方差之和,即 -generalization error=bias+variance。 +标准差公式为:$S_{N}=\sqrt{\frac{1}{N}\sum_{i=1}^{N}(x_{i}-\bar{x})^{2}}​$ -偏差(bias):描述的是预测值(估计值)的期望与真实值之间的差距。偏差越大,越偏离真实数据,如下图第二行所示。 - -方差(variance):描述的是预测值的变化范围,离散程度,也就是离其期望值的距离。方差越大,数据的分布越分散,模型的稳定程度越差。如果模型在训练集上拟合效果比较优秀,但是在测试集上拟合效果比较差劣,则方差较大,说明模型的稳定程度较差,出现这种现象可能是由于模型对训练集过拟合造成的。 如下图右列所示。 - -![](./img/ch2/2-4.png) - -简单的总结一下: -偏差大,会造成模型欠拟合; -方差大,会造成模型过拟合。 - -### 2.16.21为什么使用标准差? - -标准差公式为:$S_{N}=\sqrt{\frac{1}{N}\sum_{i=1}^{N}(x_{i}-\bar{x})^{2}}$ - -样本标准差公式为:$S_{N}=\sqrt{\frac{1}{N-1}\sum_{i=1}^{N}(x_{i}-\bar{x})^{2}}$ +样本标准差公式为:$S_{N}=\sqrt{\frac{1}{N-1}\sum_{i=1}^{N}(x_{i}-\bar{x})^{2}}​$ 与方差相比,使用标准差来表示数据点的离散程度有3个好处: 1、表示离散程度的数字与样本数据点的数量级一致,更适合对数据样本形成感性认知。 @@ -1196,123 +1362,79 @@ generalization error=bias+variance。 2、表示离散程度的数字单位与样本数据的单位一致,更方便做后续的分析运算。 3、在样本数据大致符合正态分布的情况下,标准差具有方便估算的特性:66.7%的数据点落在平均值前后1个标准差的范围内、95%的数据点落在平均值前后2个标准差的范围内,而99%的数据点将会落在平均值前后3个标准差的范围内。 -### 2.16.22点估计思想 -点估计:用实际样本的一个指标来估计总体的一个指标的一种估计方法。 - -点估计举例:比如说,我们想要了解中国人的平均身高,那么在大街上随便找了一个人,通过测量这个人的身高来估计中国人的平均身高水平;或者在淘宝上买东西的时候随便一次买到假货就说淘宝上都是假货等;这些都属于点估计。 - -点估计主要思想:在样本数据中得到一个指标,通过这个指标来估计总体指标;比如我们用样本均数来估计总体均数,样本均数就是我们要找到的指标。 - -### 2.16.23 点估计优良性原则? -获取样本均数指标相对来说比较简单,但是并不是总体的所有指标都很容易在样本中得到,比如说总体的标准差用样本的哪个指标来估计呢? - -优良性准则有两大类:一类是小样本准则,即在样本大小固定时的优良性准则;另一类是大样本准则,即在样本大小趋于无穷时的优良性准则。最重要的小样本优良性准则是无偏性及与此相关的一致最小方差无偏计。 - -样本中用来估计总体的指标要符合以下规则: - -1.首先必须是无偏统计量。 -所谓无偏性,即数学期望等于总体相应的统计量的样本估计量。 - -2.最小方差准则 -针对总体样本的无偏估计量不唯一的情况,需选用其他准则,例如最小方差准则。如果一个统计量具有最小方差,也就是说所有的样本点与此统计量的离差平方和最小,则这个统计量被称为最小平方无偏估计量。 -最大概率准则 - -4、缺一交叉准则 -在非参数回归中好像用的是缺一交叉准则 - -要明白一个原则:计算样本的任何分布、均数、标准差都是没有任何意义的,如果样本的这种计算不能反映总体的某种特性。 - -### 2.16.24 点估计、区间估计、中心极限定理之间的联系? -https://www.zhihu.com/question/21871331#answer-4090464 -点估计:是用样本统计量来估计总体参数,因为样本统计量为数轴上某一点值,估计的结果也以一个点的数值表示,所以称为点估计。 - -区间估计:通过从总体中抽取的样本,根据一定的正确度与精确度的要求,构造出适当的区间,以作为总体的分布参数(或参数的函数)的真值所在范围的估计。 -中心极限定理:设从均值为、方差为;(有限)的任意一个总体中抽取样本量为n的样本,当n充分大时,样本均值的抽样分布近似服从均值为、方差为的正态分布。 - -三者之间联系: - -1、中心极限定理是推断统计的理论基础,推断统计包括参数估计和假设检验,其中参数估计包括点估计和区间估计,所以说,中心极限定理也是点估计和区间估计的理论基础。 - -2、参数估计有两种方法:点估计和区间估计,区间估计包含了点估计。 - -相同点:都是基于一个样本作出; - -不同点:点估计只提供单一的估计值,而区间估计基于点估计还提供误差界限,给出了置信区间,受置信度的影响。 ### 2.16.25 类别不平衡产生原因? -类别不平衡(class-imbalance)是指分类任务中不同类别的训练样例数目差别很大的情况。 +​ 类别不平衡(class-imbalance)是指分类任务中不同类别的训练样例数目差别很大的情况。 产生原因: -通常分类学习算法都会假设不同类别的训练样例数目基本相同。如果不同类别的训练样例数目差别很大,则会影响学习结果,测试结果变差。例如二分类问题中有998个反例,正例有2个,那学习方法只需返回一个永远将新样本预测为反例的分类器,就能达到99.8%的精度;然而这样的分类器没有价值。 +​ 分类学习算法通常都会假设不同类别的训练样例数目基本相同。如果不同类别的训练样例数目差别很大,则会影响学习结果,测试结果变差。例如二分类问题中有998个反例,正例有2个,那学习方法只需返回一个永远将新样本预测为反例的分类器,就能达到99.8%的精度;然而这样的分类器没有价值。 ### 2.16.26 常见的类别不平衡问题解决方法 -http://blog.csdn.net/u013829973/article/details/77675147 -   防止类别不平衡对学习造成的影响,在构建分类模型之前,需要对分类不平衡性问题进行处理。主要解决方法有: 1、扩大数据集 -增加包含小类样本数据的数据,更多的数据能得到更多的分布信息。 +​ 增加包含小类样本数据的数据,更多的数据能得到更多的分布信息。 2、对大类数据欠采样 -减少大类数据样本个数,使与小样本个数接近。 -缺点:欠采样操作时若随机丢弃大类样本,可能会丢失重要信息。 -代表算法:EasyEnsemble。利用集成学习机制,将大类划分为若干个集合供不同的学习器使用。相当于对每个学习器都进行了欠采样,但在全局来看却不会丢失重要信息。 +​ 减少大类数据样本个数,使与小样本个数接近。 +​ 缺点:欠采样操作时若随机丢弃大类样本,可能会丢失重要信息。 +​ 代表算法:EasyEnsemble。其思想是利用集成学习机制,将大类划分为若干个集合供不同的学习器使用。相当于对每个学习器都进行欠采样,但对于全局则不会丢失重要信息。 3、对小类数据过采样 -过采样:对小类的数据样本进行采样来增加小类的数据样本个数。 +​ 过采样:对小类的数据样本进行采样来增加小类的数据样本个数。 -代表算法:SMOTE和ADASYN。 +​ 代表算法:SMOTE和ADASYN。 -SMOTE:通过对训练集中的小类数据进行插值来产生额外的小类样本数据。 +​ SMOTE:通过对训练集中的小类数据进行插值来产生额外的小类样本数据。 -新的少数类样本产生的策略:对每个少数类样本a,在a的最近邻中随机选一个样本b,然后在a、b之间的连线上随机选一点作为新合成的少数类样本。 -ADASYN:根据学习难度的不同,对不同的少数类别的样本使用加权分布,对于难以学习的少数类的样本,产生更多的综合数据。 通过减少类不平衡引入的偏差和将分类决策边界自适应地转移到困难的样本两种手段,改善了数据分布。 +​ 新的少数类样本产生的策略:对每个少数类样本a,在a的最近邻中随机选一个样本b,然后在a、b之间的连线上随机选一点作为新合成的少数类样本。 +​ ADASYN:根据学习难度的不同,对不同的少数类别的样本使用加权分布,对于难以学习的少数类的样本,产生更多的综合数据。 通过减少类不平衡引入的偏差和将分类决策边界自适应地转移到困难的样本两种手段,改善了数据分布。 4、使用新评价指标 -如果当前评价指标不适用,则应寻找其他具有说服力的评价指标。比如准确度这个评价指标在类别不均衡的分类任务中并不适用,甚至进行误导。因此在类别不均衡分类任务中,需要使用更有说服力的评价指标来对分类器进行评价。 +​ 如果当前评价指标不适用,则应寻找其他具有说服力的评价指标。比如准确度这个评价指标在类别不均衡的分类任务中并不适用,甚至进行误导。因此在类别不均衡分类任务中,需要使用更有说服力的评价指标来对分类器进行评价。 5、选择新算法 -不同的算法适用于不同的任务与数据,应该使用不同的算法进行比较。 +​ 不同的算法适用于不同的任务与数据,应该使用不同的算法进行比较。 6、数据代价加权 -例如当分类任务是识别小类,那么可以对分类器的小类样本数据增加权值,降低大类样本的权值,从而使得分类器将重点集中在小类样本身上。 +​ 例如当分类任务是识别小类,那么可以对分类器的小类样本数据增加权值,降低大类样本的权值,从而使得分类器将重点集中在小类样本身上。 7、转化问题思考角度 -例如在分类问题时,把小类的样本作为异常点,将问题转化为异常点检测或变化趋势检测问题。 异常点检测即是对那些罕见事件进行识别。变化趋势检测区别于异常点检测在于其通过检测不寻常的变化趋势来识别。 +​ 例如在分类问题时,把小类的样本作为异常点,将问题转化为异常点检测或变化趋势检测问题。 异常点检测即是对那些罕见事件进行识别。变化趋势检测区别于异常点检测在于其通过检测不寻常的变化趋势来识别。 8、将问题细化分析 -对问题进行分析与挖掘,将问题划分成多个更小的问题,看这些小问题是否更容易解决。 +​ 对问题进行分析与挖掘,将问题划分成多个更小的问题,看这些小问题是否更容易解决。 ## 2.17 决策树 ### 2.17.1 决策树的基本原理 -决策树是一种分而治之(Divide and Conquer)的决策过程。一个困难的预测问题, 通过树的分支节点, 被划分成两个或多个较为简单的子集,从结构上划分为不同的子问题。将依规则分割数据集的过程不断递归下去(Recursive Partitioning)。随着树的深度不断增加,分支节点的子集越来越小,所需要提的问题数也逐渐简化。当分支节点的深度或者问题的简单程度满足一定的停止规则(Stopping Rule)时, 该分支节点会停止劈分,此为自上而下的停止阈值(Cutoff Threshold)法;有些决策树也使用自下而上的剪枝(Pruning)法。 +​ 决策树是一种分而治之(Divide and Conquer)的决策过程。一个困难的预测问题, 通过树的分支节点, 被划分成两个或多个较为简单的子集,从结构上划分为不同的子问题。将依规则分割数据集的过程不断递归下去(Recursive Partitioning)。随着树的深度不断增加,分支节点的子集越来越小,所需要提的问题数也逐渐简化。当分支节点的深度或者问题的简单程度满足一定的停止规则(Stopping Rule)时, 该分支节点会停止劈分,此为自上而下的停止阈值(Cutoff Threshold)法;有些决策树也使用自下而上的剪枝(Pruning)法。 ### 2.17.2 决策树的三要素? -一棵决策树的生成过程主要分为以下3个部分: +​ 一棵决策树的生成过程主要分为以下3个部分: -特征选择:从训练数据中众多的特征中选择一个特征作为当前节点的分裂标准,如何选择特征有着很多不同量化评估标准标准,从而衍生出不同的决策树算法。 +​ 特征选择:从训练数据中众多的特征中选择一个特征作为当前节点的分裂标准,如何选择特征有着很多不同量化评估标准标准,从而衍生出不同的决策树算法。 -决策树生成:根据选择的特征评估标准,从上至下递归地生成子节点,直到数据集不可分则停止决策树停止生长。树结构来说,递归结构是最容易理解的方式。 +​ 决策树生成:根据选择的特征评估标准,从上至下递归地生成子节点,直到数据集不可分则停止决策树停止生长。树结构来说,递归结构是最容易理解的方式。 -剪枝:决策树容易过拟合,一般来需要剪枝,缩小树结构规模、缓解过拟合。剪枝技术有预剪枝和后剪枝两种。 +​ 剪枝:决策树容易过拟合,一般来需要剪枝,缩小树结构规模、缓解过拟合。剪枝技术有预剪枝和后剪枝两种。 ### 2.17.3 决策树学习基本算法 ![](./img/ch2/2-5.png) ### 2.17.4 决策树算法优缺点 -决策树算法的优点: +**决策树算法的优点**: -1、理解和解释起来简单,决策树模型易想象。 +1、决策树模型易想象,理解和解释起来简单。 2、相比于其他算法需要大量数据集而已,决策树算法要求的数据集不大。 @@ -1328,7 +1450,7 @@ ADASYN:根据学习难度的不同,对不同的少数类别的样本使用 8、效率高,决策树只需要一次构建,反复使用,每一次预测的最大计算次数不超过决策树的深度。 -决策树算法的缺点: +**决策树算法的缺点**: 1、对连续性的字段比较难预测。 @@ -1342,339 +1464,584 @@ ADASYN:根据学习难度的不同,对不同的少数类别的样本使用 6、对于各类别样本数量不一致的数据,在决策树当中,信息增益的结果偏向于那些具有更多数值的特征。 -### 2.17.5熵的概念以及理解 - -熵:度量随机变量的不确定性。 - -定义:假设随机变量X的可能取值有$x_{1},x_{2},...,x_{n}$,对于每一个可能的取值$x_{i}$,其概率为$P(X=x_{i})=p_{i},i=1,2...,n$。随机变量的熵为: +### 2.17.5 熵的概念以及理解 -$H(X)=-\sum_{i=1}^{n}p_{i}log_{2}p_{i}$ + 熵:度量随机变量的不确定性。 -对于样本集合 ,假设样本有k个类别,每个类别的概率为$\frac{|C_{k}|}{|D|}$,其中 ${|C_{k}|}{|D|}$为类别为k的样本个数,$|D|$为样本总数。样本集合D的熵为: -$H(D)=-\sum_{k=1}^{k}\frac{|C_{k}|}{|D|}log_{2}\frac{|C_{k}|}{|D|}$ +​ 定义:假设随机变量X的可能取值有$x_{1},x_{2},...,x_{n}$,对于每一个可能的取值$x_{i}$,其概率为$P(X=x_{i})=p_{i},i=1,2...,n$。随机变量的熵为: +$$ +H(X)=-\sum_{i=1}^{n}p_{i}log_{2}p_{i} +$$ +​ 对于样本集合 ,假设样本有k个类别,每个类别的概率为$\frac{|C_{k}|}{|D|}$,其中 ${|C_{k}|}{|D|}$为类别为k的样本个数,$|D|​$为样本总数。样本集合D的熵为: +$$ +H(D)=-\sum_{k=1}^{k}\frac{|C_{k}|}{|D|}log_{2}\frac{|C_{k}|}{|D|} +$$ ### 2.17.6 信息增益的理解 -定义:以某特征划分数据集前后的熵的差值。 -熵可以表示样本集合的不确定性,熵越大,样本的不确定性就越大。因此可以使用划分前后集合熵的差值来衡量使用当前特征对于样本集合D划分效果的好坏。 -假设划分前样本集合D的熵为H(D)。使用某个特征A划分数据集D,计算划分后的数据子集的熵为H(D|A)。 - -则信息增益为: - -$g(D,A)=H(D)-H(D|A)$ +​ 定义:以某特征划分数据集前后的熵的差值。 +​ 熵可以表示样本集合的不确定性,熵越大,样本的不确定性就越大。因此可以使用划分前后集合熵的差值来衡量使用当前特征对于样本集合D划分效果的好坏。 +​ 假设划分前样本集合D的熵为H(D)。使用某个特征A划分数据集D,计算划分后的数据子集的熵为H(D|A)。 -注:在决策树构建的过程中我们总是希望集合往最快到达纯度更高的子集合方向发展,因此我们总是选择使得信息增益最大的特征来划分当前数据集D。 +​ 则信息增益为: +$$ +g(D,A)=H(D)-H(D|A) +$$ +​ 注:在决策树构建的过程中我们总是希望集合往最快到达纯度更高的子集合方向发展,因此我们总是选择使得信息增益最大的特征来划分当前数据集D。 -思想:计算所有特征划分数据集D,得到多个特征划分数据集D的信息增益,从这些信息增益中选择最大的,因而当前结点的划分特征便是使信息增益最大的划分所使用的特征。 +​ 思想:计算所有特征划分数据集D,得到多个特征划分数据集D的信息增益,从这些信息增益中选择最大的,因而当前结点的划分特征便是使信息增益最大的划分所使用的特征。 另外这里提一下信息增益比相关知识: -信息增益比=惩罚参数X信息增益。 +​ 信息增益比=惩罚参数X信息增益。 -信息增益比本质:在信息增益的基础之上乘上一个惩罚参数。特征个数较多时,惩罚参数较小;特征个数较少时,惩罚参数较大。 +​ 信息增益比本质:在信息增益的基础之上乘上一个惩罚参数。特征个数较多时,惩罚参数较小;特征个数较少时,惩罚参数较大。 -惩罚参数:数据集D以特征A作为随机变量的熵的倒数。 +​ 惩罚参数:数据集D以特征A作为随机变量的熵的倒数。 ### 2.17.7 剪枝处理的作用及策略? -剪枝处理是决策树学习算法用来解决过拟合的一种办法。 +​ 剪枝处理是决策树学习算法用来解决过拟合的一种办法。 -在决策树算法中,为了尽可能正确分类训练样本, 节点划分过程不断重复, 有时候会造成决策树分支过多,以至于将训练样本集自身特点当作泛化特点, 而导致过拟合。 因此可以采用剪枝处理来去掉一些分支来降低过拟合的风险。 +​ 在决策树算法中,为了尽可能正确分类训练样本, 节点划分过程不断重复, 有时候会造成决策树分支过多,以至于将训练样本集自身特点当作泛化特点, 而导致过拟合。 因此可以采用剪枝处理来去掉一些分支来降低过拟合的风险。 -剪枝的基本策略有预剪枝(prepruning)和后剪枝(postprunint)。 +​ 剪枝的基本策略有预剪枝(prepruning)和后剪枝(postprunint)。 -预剪枝:在决策树生成过程中,在每个节点划分前先估计其划分后的泛化性能, 如果不能提升,则停止划分,将当前节点标记为叶结点。 +​ 预剪枝:在决策树生成过程中,在每个节点划分前先估计其划分后的泛化性能, 如果不能提升,则停止划分,将当前节点标记为叶结点。 -后剪枝:生成决策树以后,再自下而上对非叶结点进行考察, 若将此节点标记为叶结点可以带来泛化性能提升,则修改之。 +​ 后剪枝:生成决策树以后,再自下而上对非叶结点进行考察, 若将此节点标记为叶结点可以带来泛化性能提升,则修改之。 ## 2.18 支持向量机 ### 2.18.1 什么是支持向量机 -SVM - Support Vector Machine。支持向量机,其含义是通过支持向量运算的分类器。其中“机”的意思是机器,可以理解为分类器。 +​ 支持向量:在求解的过程中,会发现只根据部分数据就可以确定分类器,这些数据称为支持向量。 -什么是支持向量呢?在求解的过程中,会发现只根据部分数据就可以确定分类器,这些数据称为支持向量。 +​ 支持向量机(Support Vector Machine,SVM):其含义是通过支持向量运算的分类器。 -见下图,在一个二维环境中,其中点R,S,G点和其它靠近中间黑线的点可以看作为支持向量,它们可以决定分类器,也就是黑线的具体参数。 +​ 在一个二维环境中,其中点R,S,G点和其它靠近中间黑线的点可以看作为支持向量,它们可以决定分类器,黑线的具体参数。 ![](./img/ch2/2-6.png) -### 2.18.2 支持向量机解决的问题? -https://www.cnblogs.com/steven-yang/p/5658362.html -解决的问题: +​ 支持向量机(support vector machines)是一种二分类模型,它的目的是寻找一个超平面来对样本进行分割,分割的原则是间隔最大化,最终转化为一个凸二次规划问题来求解。由简至繁的模型包括: -线性分类 +​ 当训练样本线性可分时,通过硬间隔最大化,学习一个线性可分支持向量机; -在训练数据中,每个数据都有n个的属性和一个二类类别标志,我们可以认为这些数据在一个n维空间里。我们的目标是找到一个n-1维的超平面(hyperplane),这个超平面可以将数据分成两部分,每部分数据都属于同一个类别。 +​ 当训练样本近似线性可分时,通过软间隔最大化,学习一个线性支持向量机; -其实这样的超平面有很多,我们要找到一个最佳的。因此,增加一个约束条件:这个超平面到每边最近数据点的距离是最大的。也成为最大间隔超平面(maximum-margin hyperplane)。这个分类器也成为最大间隔分类器(maximum-margin classifier)。 +​ 当训练样本线性不可分时,通过核技巧和软间隔最大化,学习一个非线性支持向量机; -支持向量机是一个二类分类器。 +### 2.18.2 支持向量机能解决哪些问题? -非线性分类 +**线性分类** -SVM的一个优势是支持非线性分类。它结合使用拉格朗日乘子法和KKT条件,以及核函数可以产生非线性分类器。 +​ 在训练数据中,每个数据都有n个的属性和一个二类类别标志,我们可以认为这些数据在一个n维空间里。我们的目标是找到一个n-1维的超平面,这个超平面可以将数据分成两部分,每部分数据都属于同一个类别。 -分类器1 - 线性分类器 +​ 这样的超平面有很多,假如我们要找到一个最佳的。此时,增加一个约束条件:要求这个超平面到每边最近数据点的距离是最大的,成为最大间隔超平面。这个分类器即为最大间隔分类器。 -是一个线性函数,可以用于线性分类。一个优势是不需要样本数据。 +**非线性分类** -classifier 1: -f(x)=xwT+b(1) -(1)f(x)=xwT+b +​ SVM的一个优势是支持非线性分类。它结合使用拉格朗日乘子法和KKT条件,以及核函数可以产生非线性分类器。 -ww 和 bb 是训练数据后产生的值。 +### 2.18.3 核函数特点及其作用? +​ 引入核函数目的:把原坐标系里线性不可分的数据用Kernel投影到另一个空间,尽量使得数据在新的空间里线性可分。 -分类器2 - 非线性分类器 +​ 核函数方法的广泛应用,与其特点是分不开的: -支持线性分类和非线性分类。需要部分样本数据(支持向量),也就是$\alpha_i \ne 0$ 的数据。 +1)核函数的引入避免了“维数灾难”,大大减小了计算量。而输入空间的维数n对核函数矩阵无影响,因此,核函数方法可以有效处理高维输入。 + +2)无需知道非线性变换函数Φ的形式和参数. + +3)核函数的形式和参数的变化会隐式地改变从输入空间到特征空间的映射,进而对特征空间的性质产生影响,最终改变各种核函数方法的性能。 + +4)核函数方法可以和不同的算法相结合,形成多种不同的基于核函数技术的方法,且这两部分的设计可以单独进行,并可以为不同的应用选择不同的核函数和算法。 + +### 2.18.4 SVM为什么引入对偶问题? + +1,对偶问题将原始问题中的约束转为了对偶问题中的等式约束,对偶问题往往更加容易求解。 + +2,可以很自然的引用核函数(拉格朗日表达式里面有内积,而核函数也是通过内积进行映射的)。 + +3,在优化理论中,目标函数 f(x) 会有多种形式:如果目标函数和约束条件都为变量 x 的线性函数, 称该问题为线性规划; 如果目标函数为二次函数, 约束条件为线性函数, 称该最优化问题为二次规划; 如果目标函数或者约束条件均为非线性函数, 称该最优化问题为非线性规划。每个线性规划问题都有一个与之对应的对偶问题,对偶问题有非常良好的性质,以下列举几个: +​ a, 对偶问题的对偶是原问题; + +​ b, 无论原始问题是否是凸的,对偶问题都是凸优化问题; + +​ c, 对偶问题可以给出原始问题一个下界; + +​ d, 当满足一定条件时,原始问题与对偶问题的解是完全等价的 + +### 2.18.5 如何理解SVM中的对偶问题 + +在硬间隔支持向量机中,问题的求解可以转化为凸二次规划问题。 + +​ 假设优化目标为 $$ -w=∑ni=1αiyixiw=∑i=1nαiyixi +\begin{align} +&\min_{\boldsymbol w, b}{\frac 1 2}||\boldsymbol w||^2\\ +&s.t. y_i(\boldsymbol w^T\boldsymbol x_i+b)\geq1, i=1,2,\cdots,m.\\ +\end{align} \tag{1} $$ +**step 1**. 转化问题: +$$ +\min_{\boldsymbol w, b} \max_{\alpha_i \geq 0} \left\{{\frac 1 2}||\boldsymbol w||^2 + \sum_{i=1}^m\alpha_i(1 - y_i(\boldsymbol w^T\boldsymbol x_i+b))\right\} \tag{2} +$$ +上式等价于原问题,因为若满足(1)中不等式约束,则(2)式求max时,$\alpha_i(1 - y_i(\boldsymbol w^T\boldsymbol x_i+b))$必须取0,与(1)等价;若不满足(1)中不等式约束,(2)中求max会得到无穷大。 交换min和max获得其对偶问题: +$$ +\max_{\alpha_i \geq 0} \min_{\boldsymbol w, b} \left\{{\frac 1 2}||\boldsymbol w||^2 + \sum_{i=1}^m\alpha_i(1 - y_i(\boldsymbol w^T\boldsymbol x_i+b))\right\} +$$ +交换之后的对偶问题和原问题并不相等,上式的解小于等于原问题的解。 -classifier 2: +**step 2**.现在的问题是如何找到问题(1) 的最优值的一个最好的下界? +$$ +{\frac 1 2}||\boldsymbol w||^2 < v\\ +1 - y_i(\boldsymbol w^T\boldsymbol x_i+b) \leq 0\tag{3} +$$ +若方程组(3)无解, 则v是问题(1)的一个下界。若(3)有解, 则 +$$ +\forall \boldsymbol \alpha > 0 , \ \min_{\boldsymbol w, b} \left\{{\frac 1 2}||\boldsymbol w||^2 + \sum_{i=1}^m\alpha_i(1 - y_i(\boldsymbol w^T\boldsymbol x_i+b))\right\} < v +$$ +由逆否命题得:若 +$$ +\exists \boldsymbol \alpha > 0 , \ \min_{\boldsymbol w, b} \left\{{\frac 1 2}||\boldsymbol w||^2 + \sum_{i=1}^m\alpha_i(1 - y_i(\boldsymbol w^T\boldsymbol x_i+b))\right\} \geq v +$$ +则(3)无解。 -f(x)=∑ni=1αiyiK(xi,x)+bherexi : training data iyi : label value of training data iαi : Lagrange multiplier of training data iK(x1,x2)=exp(−∥x1−x2∥22σ2) : kernel function(2) -(2)f(x)=∑i=1nαiyiK(xi,x)+bherexi : training data iyi : label value of training data iαi : Lagrange multiplier of training data iK(x1,x2)=exp(−‖x1−x2‖22σ2) : kernel function +那么v是问题 -αα, σσ 和 bb 是训练数据后产生的值。 -可以通过调节σσ来匹配维度的大小,σσ越大,维度越低。 +(1)的一个下界。 + 要求得一个好的下界,取最大值即可 +$$ +\max_{\alpha_i \geq 0} \min_{\boldsymbol w, b} \left\{{\frac 1 2}||\boldsymbol w||^2 + \sum_{i=1}^m\alpha_i(1 - y_i(\boldsymbol w^T\boldsymbol x_i+b))\right\} +$$ +**step 3**. 令 +$$ +L(\boldsymbol w, b,\boldsymbol a) = {\frac 1 2}||\boldsymbol w||^2 + \sum_{i=1}^m\alpha_i(1 - y_i(\boldsymbol w^T\boldsymbol x_i+b)) +$$ +$p^*$为原问题的最小值,对应的$w,b$分别为$w^*,b^*$,则对于任意的$a>0$: +$$ +p^* = {\frac 1 2}||\boldsymbol w^*||^2 \geq L(\boldsymbol w^*, b,\boldsymbol a) \geq \min_{\boldsymbol w, b} L(\boldsymbol w, b,\boldsymbol a) +$$ +则 $\min_{\boldsymbol w, b} L(\boldsymbol w, b,\boldsymbol a)$是问题(1)的一个下届。 -### 2.18.3 核函数作用? +此时,取最大值即可求得好的下界,即 +$$ +\max_{\alpha_i \geq 0} \min_{\boldsymbol w, b} L(\boldsymbol w, b,\boldsymbol a) +$$ -核函数目的:把原坐标系里线性不可分的数据用Kernel投影到另一个空间,尽量使得数据在新的空间里线性可分。 +### 2.18.7 常见的核函数有哪些? +| 核函数 | 表达式 | 备注 | +| ---------------------------- | ------------------------------------------------------------ | ----------------------------------- | +| Linear Kernel线性核 | $k(x,y)=xy$ | | +| Polynomial Kernel多项式核 | $k(x,y)=(ax^{t}y+c)^{d}$ | $d>=1$为多项式的次数 | +| Exponential Kernel指数核函数 | $k(x,y)=exp(-\frac{\left \|x-y \right \|}{2\sigma ^{2}})$ | $\sigma>0$ | +| Gaussian Kernel高斯核函数 | $k(x,y)=exp(-\frac{\left \|x-y \right \|^{2}}{2\sigma ^{2}})$ | $\sigma$为高斯核的带宽,$\sigma>0$, | +| Laplacian Kernel拉普拉斯核 | $k(x,y)=exp(-\frac{\left \|x-y \right|}{\sigma})$ | $\sigma>0$ | +| ANOVA Kernel | $k(x,y)=exp(-\sigma(x^{k}-y^{k})^{2})^{d}$ | | +| Sigmoid Kernel | $k(x,y)=tanh(ax^{t}y+c)$ | $tanh$为双曲正切函数,$a>0,c<0$ | -核函数方法的广泛应用,与其特点是分不开的: +### 2.18.9 SVM主要特点? -1)核函数的引入避免了“维数灾难”,大大减小了计算量。而输入空间的维数n对核函数矩阵无影响,因此,核函数方法可以有效处理高维输入。 +特点: -2)无需知道非线性变换函数Φ的形式和参数. +(1) SVM方法的理论基础是非线性映射,SVM利用内积核函数代替向高维空间的非线性映射; -3)核函数的形式和参数的变化会隐式地改变从输入空间到特征空间的映射,进而对特征空间的性质产生影响,最终改变各种核函数方法的性能。 +(2) SVM的目标是对特征空间划分得到最优超平面,SVM方法核心是最大化分类边际; -4)核函数方法可以和不同的算法相结合,形成多种不同的基于核函数技术的方法,且这两部分的设计可以单独进行,并可以为不同的应用选择不同的核函数和算法。 +(3) 支持向量是SVM的训练结果,在SVM分类决策中起决定作用的是支持向量。 -### 2.18.4 对偶问题 -### 2.18.5 理解支持向量回归 -http://blog.csdn.net/liyaohhh/article/details/51077082 +(4) SVM 是一种有坚实理论基础的新颖的小样本学习方法。它基本上不涉及概率测度及大数定律等,也简化了通常的分类和回归等问题。 -### 2.18.6 理解SVM(核函数) -http://blog.csdn.net/Love_wanling/article/details/69390047 +(5) SVM 的最终决策函数只由少数的支持向量所确定,计算的复杂性取决于支持向量的数目,而不是样本空间的维数,这在某种意义上避免了“维数灾难”。 -### 2.18.7 常见的核函数有哪些? -http://blog.csdn.net/Love_wanling/article/details/69390047 +(6) 少数支持向量决定了最终结果,这不但可以帮助我们抓住关键样本、“剔除”大量冗余样本,而且注定了该方法不但算法简单,而且具有较好的“鲁棒”性。这种“鲁棒”性主要体现在: -本文将遇到的核函数进行收集整理,分享给大家。 -http://blog.csdn.net/wsj998689aa/article/details/47027365 +​ ①增、删非支持向量样本对模型没有影响; -1.Linear Kernel -线性核是最简单的核函数,核函数的数学公式如下: +​ ②支持向量样本集具有一定的鲁棒性; -$k(x,y)=xy$ +​ ③有些成功的应用中,SVM 方法对核的选取不敏感 -如果我们将线性核函数应用在KPCA中,我们会发现,推导之后和原始PCA算法一模一样,很多童鞋借此说“kernel is shit!!!”,这是不对的,这只是线性核函数偶尔会出现等价的形式罢了。 +(7) SVM学习问题可以表示为凸优化问题,因此可以利用已知的有效算法发现目标函数的全局最小值。而其他分类方法(如基于规则的分类器和人工神经网络)都采用一种基于贪心学习的策略来搜索假设空间,这种方法一般只能获得局部最优解。 -2.Polynomial Kernel +(8) SVM通过最大化决策边界的边缘来控制模型的能力。尽管如此,用户必须提供其他参数,如使用核函数类型和引入松弛变量等。 -多项式核实一种非标准核函数,它非常适合于正交归一化后的数据,其具体形式如下: +(9) SVM在小样本训练集上能够得到比其它算法好很多的结果。SVM优化目标是结构化风险最小,而不是经验风险最小,避免了过学习问题,通过margin的概念,得到对数据分布的结构化描述,减低了对数据规模和数据分布的要求,有优秀的泛化能力。 -$k(x,y)=(ax^{t}y+c)^{d}$ +(10) 它是一个凸优化问题,因此局部最优解一定是全局最优解的优点。 -这个核函数是比较好用的,就是参数比较多,但是还算稳定。 +### 2.18.9 SVM主要缺点? -3.Gaussian Kernel +(1) SVM算法对大规模训练样本难以实施 -这里说一种经典的鲁棒径向基核,即高斯核函数,鲁棒径向基核对于数据中的噪音有着较好的抗干扰能力,其参数决定了函数作用范围,超过了这个范围,数据的作用就“基本消失”。高斯核函数是这一族核函数的优秀代表,也是必须尝试的核函数,其数学形式如下: +​ SVM的空间消耗主要是存储训练样本和核矩阵,由于SVM是借助二次规划来求解支持向量,而求解二次规划将涉及m阶矩阵的计算(m为样本的个数),当m数目很大时该矩阵的存储和计算将耗费大量的机器内存和运算时间。 -$k(x,y)=exp(-\frac{\left \| x-y \right \|^{2}}{2\sigma ^{2}})$ +​ 如果数据量很大,SVM的训练时间就会比较长,如垃圾邮件的分类检测,没有使用SVM分类器,而是使用了简单的naive bayes分类器,或者是使用逻辑回归模型分类。 -虽然被广泛使用,但是这个核函数的性能对参数十分敏感,以至于有一大把的文献专门对这种核函数展开研究,同样,高斯核函数也有了很多的变种,如指数核,拉普拉斯核等。 +(2) 用SVM解决多分类问题存在困难 -4.Exponential Kernel +​ 经典的支持向量机算法只给出了二类分类的算法,而在实际应用中,一般要解决多类的分类问题。可以通过多个二类支持向量机的组合来解决。主要有一对多组合模式、一对一组合模式和SVM决策树;再就是通过构造多个分类器的组合来解决。主要原理是克服SVM固有的缺点,结合其他算法的优势,解决多类问题的分类精度。如:与粗集理论结合,形成一种优势互补的多类问题的组合分类器。 -指数核函数就是高斯核函数的变种,它仅仅是将向量之间的L2距离调整为L1距离,这样改动会对参数的依赖性降低,但是适用范围相对狭窄。其数学形式如下: +(3)对缺失数据敏感,对参数和核函数的选择敏感 -$k(x,y)=exp(-\frac{\left \| x-y \right \|}{2\sigma ^{2}})$ +​ 支持向量机性能的优劣主要取决于核函数的选取,所以对于一个实际问题而言,如何根据实际的数据模型选择合适的核函数从而构造SVM算法.目前比较成熟的核函数及其参数的选择都是人为的,根据经验来选取的,带有一定的随意性.在不同的问题领域,核函数应当具有不同的形式和参数,所以在选取时候应该将领域知识引入进来,但是目前还没有好的方法来解决核函数的选取问题. -5.Laplacian Kernel +### 2.18.10 逻辑回归与SVM的异同 -拉普拉斯核完全等价于指数核,唯一的区别在于前者对参数的敏感性降低,也是一种径向基核函数。 +相同点: -$k(x,y)=exp(-\frac{\left \| x-y \right \|}{\sigma })$ +- LR和SVM都是**分类**算法 +- LR和SVM都是**监督学习**算法。 +- LR和SVM都是**判别模型**。 +- 如果不考虑核函数,LR和SVM都是**线性分类**算法,也就是说他们的分类决策面都是线性的。 + 说明:LR也是可以用核函数的.但LR通常不采用核函数的方法.(**计算量太大**) -6.ANOVA Kernel +不同点: -ANOVA 核也属于径向基核函数一族,其适用于多维回归问题,数学形式如下: +**1、LR采用log损失,SVM采用合页(hinge)损失。** +逻辑回归的损失函数: +$$ +J(\theta)=-\frac{1}{m}\left[\sum^m_{i=1}y^{(i)}logh_{\theta}(x^{(i)})+ (1-y^{(i)})log(1-h_{\theta}(x^{(i)}))\right] +$$ +支持向量机的目标函数: +$$ +L(w,n,a)=\frac{1}{2}||w||^2-\sum^n_{i=1}\alpha_i \left( y_i(w^Tx_i+b)-1\right) +$$ +​ 逻辑回归方法基于概率理论,假设样本为1的概率可以用sigmoid函数来表示,然后通过**极大似然估计**的方法估计出参数的值。 -$k(x,y)=exp(-\sigma(x^{k}-y^{k})^{2})^{d}$ +​ 支持向量机基于几何**间隔最大化**原理,认为存在最大几何间隔的分类面为最优分类面。 -7.Sigmoid Kernel +2、**LR对异常值敏感,SVM对异常值不敏感**。 -Sigmoid 核来源于神经网络,现在已经大量应用于深度学习,是当今机器学习的宠儿,它是S型的,所以被用作于“激活函数”。关于这个函数的性质可以说好几篇文献,大家可以随便找一篇深度学习的文章看看。 +​ 支持向量机只考虑局部的边界线附近的点,而逻辑回归考虑全局。LR模型找到的那个超平面,是尽量让所有点都远离他,而SVM寻找的那个超平面,是只让最靠近中间分割线的那些点尽量远离,即只用到那些支持向量的样本。 -$k(x,y)=tanh(ax^{t}y+c)$ +支持向量机改变非支持向量样本并不会引起决策面的变化。 -8.Rational Quadratic Kernel -二次有理核完完全全是作为高斯核的替代品出现,如果你觉得高斯核函数很耗时,那么不妨尝试一下这个核函数,顺便说一下,这个核函数作用域虽广,但是对参数十分敏感,慎用!!!! +逻辑回归中改变任何样本都会引起决策面的变化。 -$k(x,y)=1-\frac{\left \| x-y \right \|^{2}}{\left \| x-y \right \|^{2}+c}$ +**3、计算复杂度不同。对于海量数据,SVM的效率较低,LR效率比较高** -### 2.18.8 软间隔与正则化 -### 2.18.9 SVM主要特点及缺点? +​ 当样本较少,特征维数较低时,SVM和LR的运行时间均比较短,SVM较短一些。准确率的话,LR明显比SVM要高。当样本稍微增加些时,SVM运行时间开始增长,但是准确率赶超了LR。SVM时间虽长,但在接收范围内。当数据量增长到20000时,特征维数增长到200时,SVM的运行时间剧烈增加,远远超过了LR的运行时间。但是准确率却和LR相差无几。(这其中主要原因是大量非支持向量参与计算,造成SVM的二次规划问题) -http://www.elecfans.com/emb/fpga/20171118582139_2.html +**4、对非线性问题的处理方式不同,LR主要靠特征构造,必须组合交叉特征,特征离散化。SVM也可以这样,还可以通过kernel(因为只有支持向量参与核计算,计算复杂度不高)。**(由于可以利用核函数,。SVM则可以通过对偶求解高效处理。LR则在特征空间维度很高时,表现较差。) -3.3.2.1 SVM有如下主要几个特点: +**5、SVM的损失函数就自带正则!!!(损失函数中的1/2||w||^2项),这就是为什么SVM是结构风险最小化算法的原因!!!而LR必须另外在损失函数上添加正则项!!!** -(1)非线性映射是SVM方法的理论基础,SVM利用内积核函数代替向高维空间的非线性映射; -(2)对特征空间划分的最优超平面是SVM的目标,最大化分类边际的思想是SVM方法的核心; -(3)支持向量是SVM的训练结果,在SVM分类决策中起决定作用的是支持向量。 -(4)SVM 是一种有坚实理论基础的新颖的小样本学习方法。它基本上不涉及概率测度及大数定律等,因此不同于现有的统计方法。从本质上看,它避开了从归纳到演绎的传统过程,实现了高效的从训练样本到预报样本的“转导推理”,大大简化了通常的分类和回归等问题。 -(5)SVM 的最终决策函数只由少数的支持向量所确定,计算的复杂性取决于支持向量的数目,而不是样本空间的维数,这在某种意义上避免了“维数灾难”。 -(6)少数支持向量决定了最终结果,这不但可以帮助我们抓住关键样本、“剔除”大量冗余样本,而且注定了该方法不但算法简单,而且具有较好的“鲁棒”性。这种“鲁棒”性主要体现在: -①增、删非支持向量样本对模型没有影响; -②支持向量样本集具有一定的鲁棒性; -③有些成功的应用中,SVM 方法对核的选取不敏感 +6、SVM自带**结构风险最小化**,LR则是**经验风险最小化**。 -3.3.2.2 SVM的两个不足: -(1) SVM算法对大规模训练样本难以实施 -由 于SVM是借助二次规划来求解支持向量,而求解二次规划将涉及m阶矩阵的计算(m为样本的个数),当m数目很大时该矩阵的存储和计算将耗费大量的机器内存 和运算时间。针对以上问题的主要改进有有J.Platt的SMO算法、T.Joachims的SVM、C.J.C.Burges等的PCGC、张学工的 CSVM以及O.L.Mangasarian等的SOR算法。 -(2) 用SVM解决多分类问题存在困难 -经典的支持向量机算法只给出了二类分类的算法,而在数据挖掘的实际应用中,一般要解决多类的分类问题。可以通过多个二类支持向量机的组合来解决。主要有一对多组合模式、一对一组合模式和SVM决策树;再就是通过构造多个分类器的组合来解决。主要原理是克服SVM固有的缺点,结合其他算法的优势,解决多类问题的分类精度。如:与粗集理论结合,形成一种优势互补的多类问题的组合分类器。 +7、SVM会用核函数而LR一般不用[核函数](https://www.cnblogs.com/huangyc/p/9940487.html)。 -## 2.19 贝叶斯 +## 2.19 贝叶斯分类器 ### 2.19.1 图解极大似然估计 -极大似然估计 http://blog.csdn.net/zengxiantao1994/article/details/72787849 - 极大似然估计的原理,用一张图片来说明,如下图所示: -![](./img/ch2/2-7.png) +![](./img/ch2/2.19.1.1.png) -总结起来,最大似然估计的目的就是:利用已知的样本结果,反推最有可能(最大概率)导致这样结果的参数值。 +​ 例:有两个外形完全相同的箱子,1号箱有99只白球,1只黑球;2号箱有1只白球,99只黑球。在一次实验中,取出的是黑球,请问是从哪个箱子中取出的? -原理:极大似然估计是建立在极大似然原理的基础上的一个统计方法,是概率论在统计学中的应用。极大似然估计提供了一种给定观察数据来评估模型参数的方法,即:“模型已定,参数未知”。通过若干次试验,观察其结果,利用试验结果得到某个参数值能够使样本出现的概率为最大,则称为极大似然估计。 +​ 一般的根据经验想法,会猜测这只黑球最像是从2号箱取出,此时描述的“最像”就有“最大似然”的意思,这种想法常称为“最大似然原理”。 -由于样本集中的样本都是独立同分布,可以只考虑一类样本集D,来估计参数向量θ。记已知的样本集为: +### 2.19.2 极大似然估计原理 -$D=x_{1},x_{2},...,x_{n}$ +​ 总结起来,最大似然估计的目的就是:利用已知的样本结果,反推最有可能(最大概率)导致这样结果的参数值。 +​ 极大似然估计是建立在极大似然原理的基础上的一个统计方法。极大似然估计提供了一种给定观察数据来评估模型参数的方法,即:“模型已定,参数未知”。通过若干次试验,观察其结果,利用试验结果得到某个参数值能够使样本出现的概率为最大,则称为极大似然估计。 + +​ 由于样本集中的样本都是独立同分布,可以只考虑一类样本集D,来估计参数向量θ。记已知的样本集为: +$$ +D=x_{1},x_{2},...,x_{n} +$$ 似然函数(linkehood function):联合概率密度函数$P(D|\theta )$称为相对于$x_{1},x_{2},...,x_{n}$的θ的似然函数。 +$$ +l(\theta )=p(D|\theta ) =p(x_{1},x_{2},...,x_{N}|\theta )=\prod_{i=1}^{N}p(x_{i}|\theta ) +$$ +如果$\hat{\theta}$是参数空间中能使似然函数$l(\theta)$最大的θ值,则$\hat{\theta}$应该是“最可能”的参数值,那么$\hat{\theta}​$就是θ的极大似然估计量。它是样本集的函数,记作: +$$ +\hat{\theta}=d(x_{1},x_{2},...,x_{N})=d(D) +$$ +$\hat{\theta}(x_{1},x_{2},...,x_{N})$称为极大似然函数估计值。 -$l(\theta )=p(D|\theta ) =p(x_{1},x_{2},...,x_{N}|\theta )=\prod_{i=1}^{N}p(x_{i}|\theta )$ +### 2.19.3 贝叶斯分类器基本原理 -如果$\hat{\theta}$是参数空间中能使似然函数$l(\theta)$最大的θ值,则$\hat{\theta}$应该是“最可能”的参数值,那么$\hat{\theta}$就是θ的极大似然估计量。它是样本集的函数,记作: +https://www.cnblogs.com/hxyue/p/5873566.html -$\hat{\theta}=d(x_{1},x_{2},...,x_{N})=d(D)$ +https://www.cnblogs.com/super-zhang-828/p/8082500.html -$\hat{\theta}(x_{1},x_{2},...,x_{N})$称为极大似然函数估计值。 +贝叶斯决策论通过**相关概率已知**的情况下利用**误判损失**来选择最优的类别分类。 + +假设有$N$种可能的分类标记,记为$Y=\{c_1,c_2,...,c_N\}$,那对于样本$x$,它属于哪一类呢? + +计算步骤如下: + +step 1. 算出样本$x$属于第$i$个类的概率,即$P(c_i|x)​$; + +step 2. 通过比较所有的$P(c_i|\boldsymbol{x})$,得到样本$x$所属的最佳类别。 + +step 3. 将类别$c_i$和样本$x$代入到贝叶斯公式种,得到 +$$ +P(c_i|\boldsymbol{x})=\frac{P(\boldsymbol{x}|c_i)P(c_i)}{P(\boldsymbol{x})}. +$$ +一般来说,$P(c_i)$为先验概率,$P(\boldsymbol{x}|c_i)$为条件概率,$P(\boldsymbol{x})$是用于归一化的证据因子。对于$P(c_i)$可以通过训练样本中类别为$c_i$的样本所占的比例进行估计;此外,由于只需要找出最大的$P(\boldsymbol{x}|c_i)$,因此我们并不需要计算$P(\boldsymbol{x})$. + +为了 求解条件概率,基于不同假设提出了不同的方法,以下将介绍朴素贝叶斯分类器和半朴素贝叶斯分类器。 + +### 2.19.4 朴素贝叶斯分类器 + +假设样本$x$包含$d$个属性,即$x=\{ x_1,x_2,...,x_d\}$。于是有 +$$ +P(\boldsymbol{x}|c_i)=P(x_1,x_2,\cdots,x_d|c_i). +$$ +这个联合概率难以从有限的训练样本中直接估计得到。于是,朴素贝叶斯(Naive Bayesian,简称NB)采用了“属性条件独立性假设”:对已知类别,假设所有属性相互独立。于是有 +$$ +P(x_1,x_2,\cdots,x_d|c_i)=\prod_{j=1}^d P(x_j|c_i). +$$ +这样的话,我们就可以很容易地推出相应的判定准则了: +$$ +h_{nb}(\boldsymbol{x})=\mathop{\arg \max}_{c_i\in Y} P(c_i)\prod_{j=1}^dP(x_j|c_i). +$$ +**条件概率$P(x_j|c_i)​$的求解** + +如果$x_j$是标签属性,那么我们可以通过计数的方法估计$P(x_j|c_i)$ +$$ +P(x_j|c_i)=\frac{P(x_j,c_i)}{P(c_i)}\approx\frac{\#(x_j,c_i)}{\#(c_i)}. +$$ +其中,$\#(x_j,c_i)$表示在训练样本中$x_j$与共同$c_{i}$出现的次数。 + +如果$x_j$是数值属性,通常我们假设类别中$c_{i}$的所有样本第个属$j$性的值服从正态分布。我们首先估计这个分布的均值$μ$和方差$σ$,然后计算$x_j$在这个分布中的概率密度$P(x_j|c_i)$。 + +### 2.19.5 举例理解朴素贝叶斯分类器 + +训练集如下: + +https://www.cnblogs.com/super-zhang-828/p/8082500.html + +| 编号 | 色泽 | 根蒂 | 敲声 | 纹理 | 脐部 | 触感 | 密度 | 含糖率 | 好瓜 | +| :--: | :--: | :--: | :--: | :--: | :--: | :--: | :---: | :----: | :--: | +| 1 | 青绿 | 蜷缩 | 浊响 | 清晰 | 凹陷 | 硬滑 | 0.697 | 0.460 | 是 | +| 2 | 乌黑 | 蜷缩 | 沉闷 | 清晰 | 凹陷 | 硬滑 | 0.774 | 0.376 | 是 | +| 3 | 乌黑 | 蜷缩 | 浊响 | 清晰 | 凹陷 | 硬滑 | 0.634 | 0.264 | 是 | +| 4 | 青绿 | 蜷缩 | 沉闷 | 清晰 | 凹陷 | 硬滑 | 0.608 | 0.318 | 是 | +| 5 | 浅白 | 蜷缩 | 浊响 | 清晰 | 凹陷 | 硬滑 | 0.556 | 0.215 | 是 | +| 6 | 青绿 | 稍蜷 | 浊响 | 清晰 | 稍凹 | 软粘 | 0.403 | 0.237 | 是 | +| 7 | 乌黑 | 稍蜷 | 浊响 | 稍糊 | 稍凹 | 软粘 | 0.481 | 0.149 | 是 | +| 8 | 乌黑 | 稍蜷 | 浊响 | 清晰 | 稍凹 | 硬滑 | 0.437 | 0.211 | 是 | +| 9 | 乌黑 | 稍蜷 | 沉闷 | 稍糊 | 稍凹 | 硬滑 | 0.666 | 0.091 | 否 | +| 10 | 青绿 | 硬挺 | 清脆 | 清晰 | 平坦 | 软粘 | 0.243 | 0.267 | 否 | +| 11 | 浅白 | 硬挺 | 清脆 | 模糊 | 平坦 | 硬滑 | 0.245 | 0.057 | 否 | +| 12 | 浅白 | 蜷缩 | 浊响 | 模糊 | 平坦 | 软粘 | 0.343 | 0.099 | 否 | +| 13 | 青绿 | 稍蜷 | 浊响 | 稍糊 | 凹陷 | 硬滑 | 0.639 | 0.161 | 否 | +| 14 | 浅白 | 稍蜷 | 沉闷 | 稍糊 | 凹陷 | 硬滑 | 0.657 | 0.198 | 否 | +| 15 | 乌黑 | 稍蜷 | 浊响 | 清晰 | 稍凹 | 软粘 | 0.360 | 0.370 | 否 | +| 16 | 浅白 | 蜷缩 | 浊响 | 模糊 | 平坦 | 硬滑 | 0.593 | 0.042 | 否 | +| 17 | 青绿 | 蜷缩 | 沉闷 | 稍糊 | 稍凹 | 硬滑 | 0.719 | 0.103 | 否 | + +对下面的测试例“测1”进行 分类: + +| 编号 | 色泽 | 根蒂 | 敲声 | 纹理 | 脐部 | 触感 | 密度 | 含糖率 | 好瓜 | +| :--: | :--: | :--: | :--: | :--: | :--: | :--: | :---: | :----: | :--: | +| 测1 | 青绿 | 蜷缩 | 浊响 | 清晰 | 凹陷 | 硬滑 | 0.697 | 0.460 | ? | + +首先,估计类先验概率$P(c_j)$,有 +$$ +\begin{align} +&P(好瓜=是)=\frac{8}{17}=0.471 \newline +&P(好瓜=否)=\frac{9}{17}=0.529 +\end{align} +$$ +然后,为每个属性估计条件概率(这里,对于连续属性,假定它们服从正态分布) + +![](./img/ch2/2.19.5C.png) + +于是有 +$$ +\begin{align} +P(&好瓜=是)\times P_{青绿|是} \times P_{蜷缩|是} \times P_{浊响|是} \times P_{清晰|是} \times P_{凹陷|是}\newline +&\times P_{硬滑|是} \times p_{密度:0.697|是} \times p_{含糖:0.460|是} \approx 0.063 \newline\newline +P(&好瓜=否)\times P_{青绿|否} \times P_{蜷缩|否} \times P_{浊响|否} \times P_{清晰|否} \times P_{凹陷|否}\newline +&\times P_{硬滑|否} \times p_{密度:0.697|否} \times p_{含糖:0.460|否} \approx 6.80\times 10^{-5} +\end{align} +$$ + +``` +`0.063>6.80\times 10^{-5}` +``` + +### 2.19.4 朴素贝叶斯分类器 + +​ 朴素贝叶斯采用了“属性条件独立性假设”,半朴素贝叶斯分类器的基本想法是适当考虑一部分属性间的相互依赖信息。**独依赖估计**(One-Dependent Estimator,简称ODE)是半朴素贝叶斯分类器最常用的一种策略。顾名思义,独依赖是假设每个属性在类别之外最多依赖一个其他属性,即 +$$ +P(x|c_i)=\prod_{j=1}^d P(x_j|c_i,{\rm pa}_j). +$$ +其中$pa_j$为属性$x_i$所依赖的属性,成为$x_i$的父属性。假设父属性$pa_j$已知,那么可以使用下面的公式估计$P(x_j|c_i,{\rm pa}_j)$ +$$ +P(x_j|c_i,{\rm pa}_j)=\frac{P(x_j,c_i,{\rm pa}_j)}{P(c_i,{\rm pa}_j)}. +$$ + +## 2.20 EM算法 + +### 2.20.1 EM算法基本思想 + +​ 最大期望算法(Expectation-Maximization algorithm, EM),是一类通过迭代进行极大似然估计的优化算法,通常作为牛顿迭代法的替代,用于对包含隐变量或缺失数据的概率模型进行参数估计。 -### 2.19.2 朴素贝叶斯分类器和一般的贝叶斯分类器有什么区别? -### 2.19.3 朴素与半朴素贝叶斯分类器 -### 2.19.4 贝叶斯网三种典型结构 -### 2.19.5 什么是贝叶斯错误率 -### 2.19.6 什么是贝叶斯最优错误率 -## 2.20 EM算法解决问题及实现流程 +​ 最大期望算法基本思想是经过两个步骤交替进行计算: -1.EM算法要解决的问题 +​ 第一步是计算期望(E),利用对隐藏变量的现有估计值,计算其最大似然估计值**;** - 我们经常会从样本观察数据中,找出样本的模型参数。 最常用的方法就是极大化模型分布的对数似然函数。 +​ 第二步是最大化(M),最大化在E步上求得的最大似然值来计算参数的值。 -但是在一些情况下,我们得到的观察数据有未观察到的隐含数据,此时我们未知的有隐含数据和模型参数,因而无法直接用极大化对数似然函数得到模型分布的参数。怎么办呢?这就是EM算法可以派上用场的地方了。 +​ M步上找到的参数估计值被用于下一个E步计算中,这个过程不断交替进行。 -EM算法解决这个的思路是使用启发式的迭代方法,既然我们无法直接求出模型分布参数,那么我们可以先猜想隐含数据(EM算法的E步),接着基于观察数据和猜测的隐含数据一起来极大化对数似然,求解我们的模型参数(EM算法的M步)。由于我们之前的隐藏数据是猜测的,所以此时得到的模型参数一般还不是我们想要的结果。不过没关系,我们基于当前得到的模型参数,继续猜测隐含数据(EM算法的E步),然后继续极大化对数似然,求解我们的模型参数(EM算法的M步)。以此类推,不断的迭代下去,直到模型分布参数基本无变化,算法收敛,找到合适的模型参数。 +### 2.20.2 EM算法推导 + +对于$m$个样本观察数据$x=(x^{1},x^{2},...,x^{m})$,现在想找出样本的模型参数$\theta$,其极大化模型分布的对数似然函数为: +$$ +\theta = arg \max \limits_{\theta}\sum\limits_{i=1}^m logP(x^{(i)};\theta) +$$ +如果得到的观察数据有未观察到的隐含数据$z=(z^{(1)},z^{(2)},...z^{(m)})$,极大化模型分布的对数似然函数则为: +$$ +\theta = arg \max \limits_{\theta}\sum\limits_{i=1}^m logP(x^{(i)};\theta) = arg \max \limits_{\theta}\sum\limits_{i=1}^m log\sum\limits_{z^{(i)}}P(x^{(i)}, z^{(i)};\theta) \tag{a} +$$ +由于上式不能直接求出$\theta$,采用缩放技巧: +$$ +\begin{align} \sum\limits_{i=1}^m log\sum\limits_{z^{(i)}}P(x^{(i)}, z^{(i)};\theta) & = \sum\limits_{i=1}^m log\sum\limits_{z^{(i)}}Q_i(z^{(i)})\frac{P(x^{(i)}, z^{(i)};\theta)}{Q_i(z^{(i)})} \\ & \geq \sum\limits_{i=1}^m \sum\limits_{z^{(i)}}Q_i(z^{(i)})log\frac{P(x^{(i)}, z^{(i)};\theta)}{Q_i(z^{(i)})} \end{align} \tag{1} +$$ +上式用到了Jensen不等式: +$$ +log\sum\limits_j\lambda_jy_j \geq \sum\limits_j\lambda_jlogy_j\;\;, \lambda_j \geq 0, \sum\limits_j\lambda_j =1 +$$ +并且引入了一个未知的新分布$Q_i(z^{(i)})$。 -从上面的描述可以看出,EM算法是迭代求解最大值的算法,同时算法在每一次迭代时分为两步,E步和M步。一轮轮迭代更新隐含数据和模型分布参数,直到收敛,即得到我们需要的模型参数。 +此时,如果需要满足Jensen不等式中的等号,所以有: +$$ +\frac{P(x^{(i)}, z^{(i)};\theta)}{Q_i(z^{(i)})} =c, c为常数 +$$ +由于$Q_i(z^{(i)})$是一个分布,所以满足 +$$ +\sum\limits_{z}Q_i(z^{(i)}) =1 +$$ +综上,可得: +$$ +Q_i(z^{(i)}) = \frac{P(x^{(i)}, z^{(i)};\theta)}{\sum\limits_{z}P(x^{(i)}, z^{(i)};\theta)} = \frac{P(x^{(i)}, z^{(i)};\theta)}{P(x^{(i)};\theta)} = P( z^{(i)}|x^{(i)};\theta)) +$$ +如果$Q_i(z^{(i)}) = P( z^{(i)}|x^{(i)};\theta))$ ,则第(1)式是我们的包含隐藏数据的对数似然的一个下界。如果我们能极大化这个下界,则也在尝试极大化我们的对数似然。即我们需要最大化下式: +$$ +arg \max \limits_{\theta} \sum\limits_{i=1}^m \sum\limits_{z^{(i)}}Q_i(z^{(i)})log\frac{P(x^{(i)}, z^{(i)};\theta)}{Q_i(z^{(i)})} +$$ +简化得: +$$ +arg \max \limits_{\theta} \sum\limits_{i=1}^m \sum\limits_{z^{(i)}}Q_i(z^{(i)})log{P(x^{(i)}, z^{(i)};\theta)} +$$ +以上即为EM算法的M步,$\sum\limits_{z^{(i)}}Q_i(z^{(i)})log{P(x^{(i)}, z^{(i)};\theta)}​$可理解为$logP(x^{(i)}, z^{(i)};\theta)​$基于条件概率分布$Q_i(z^{(i)})​$的期望。以上即为EM算法中E步和M步的具体数学含义。 +### 2.20.3 图解EM算法 -一个最直观了解EM算法思路的是K-Means算法,见之前写的K-Means聚类算法原理。 +​ 考虑上一节中的(a)式,表达式中存在隐变量,直接找到参数估计比较困难,通过EM算法迭代求解下界的最大值到收敛为止。 +![](./img/ch2/2.20.1.jpg) -在K-Means聚类时,每个聚类簇的质心是隐含数据。我们会假设KK个初始化质心,即EM算法的E步;然后计算得到每个样本最近的质心,并把样本聚类到最近的这个质心,即EM算法的M步。重复这个E步和M步,直到质心不再变化为止,这样就完成了K-Means聚类。 +图片中的紫色部分是我们的目标模型$p(x|\theta)$,该模型复杂,难以求解析解,为了消除隐变量$z^{(i)}$的影响,我们可以选择一个不包含$z^{(i)}$的模型$r(x|\theta)$,使其满足条件$r(x|\theta) \leq p(x|\theta)​$。 +求解步骤如下: -当然,K-Means算法是比较简单的,实际中的问题往往没有这么简单。上面对EM算法的描述还很粗糙,我们需要用数学的语言精准描述。 +(1)选取$\theta_1$,使得$r(x|\theta_1) = p(x|\theta_1)$,然后对此时的$r$求取最大值,得到极值点$\theta_2$,实现参数的更新。 -2.EM算法流程 +(2)重复以上过程到收敛为止,在更新过程中始终满足$r \leq p​$. -现在我们总结下EM算法的流程。 +### 2.20.4 EM算法流程 -输入:观察数据x=(x(1),x(2),...x(m))x=(x(1),x(2),...x(m)),联合分布p(x,z|θ)p(x,z|θ), 条件分布p(z|x,θ)p(z|x,θ), 最大迭代次数JJ。 +输入:观察数据$x=(x^{(1)},x^{(2)},...x^{(m)})$,联合分布$p(x,z ;\theta)$,条件分布$p(z|x; \theta)$,最大迭代次数$J$ -1) 随机初始化模型参数θθ的初值θ0θ0。 +1)随机初始化模型参数$\theta$的初值$\theta^0$。 -2) for j from 1 to J开始EM算法迭代: +2)$for \ j \ from \ 1 \ to \ j$: -a) E步:计算联合分布的条件概率期望: -Qi(z(i))=P(z(i)|x(i),θj))Qi(z(i))=P(z(i)|x(i),θj)) -L(θ,θj)=∑i=1m∑z(i)Qi(z(i))logP(x(i),z(i)|θ)L(θ,θj)=∑i=1m∑z(i)Qi(z(i))logP(x(i),z(i)|θ) +​ a) E步。计算联合分布的条件概率期望: +$$ +Q_i(z^{(i)}) = P( z^{(i)}|x^{(i)},\theta^{j})) +$$ -b) M步:极大化L(θ,θj)L(θ,θj),得到θj+1θj+1: -θj+1=argmaxθL(θ,θj)θj+1=argmaxθL(θ,θj) +$$ +L(\theta, \theta^{j}) = \sum\limits_{i=1}^m\sum\limits_{z^{(i)}}Q_i(z^{(i)})log{P(x^{(i)}, z^{(i)};\theta)} +$$ -c) 如果θj+1θj+1已收敛,则算法结束。否则继续回到步骤a)进行E步迭代。 +​ b) M步。极大化$L(\theta, \theta^{j})$,得到$\theta^{j+1}$: +$$ +\theta^{j+1} = arg \max \limits_{\theta}L(\theta, \theta^{j}) +$$ +​ c) 如果$\theta^{j+1}$收敛,则算法结束。否则继续回到步骤a)进行E步迭代。 -输出:模型参数θθ。 +输出:模型参数$\theta​$。 ## 2.21 降维和聚类 -### 2.21.1 为什么会产生维数灾难? +### 2.21.1 图解为什么会产生维数灾难? + +http://www.visiondummy.com/2014/04/curse-dimensionality-affect-classification/ + +​ 假如数据集包含10张照片,照片中包含三角形和圆两种形状。现在来设计一个分类器进行训练,让这个分类其模型对其他的照片进行正确分类(假设三角形和圆的总数是无限大),简单的,我们用一个特征进行分类: -http://blog.csdn.net/chenjianbo88/article/details/52382943 -假设地球上猫和狗的数量是无限的。由于有限的时间和计算能力,我们仅仅选取了10张照片作为训练样本。我们的目的是基于这10张照片来训练一个线性分类器,使得这个线性分类器可以对剩余的猫或狗的照片进行正确分类。我们从只用一个特征来辨别猫和狗开始: -![](./img/ch2/2-8.png) +![](./img/ch2/2.21.1.1.png) -从图2可以看到,如果仅仅只有一个特征的话,猫和狗几乎是均匀分布在这条线段上,很难将10张照片线性分类。那么,增加一个特征后的情况会怎么样: +​ 图2.21.1.a -![](./img/ch2/2-9.png) +​ 从上图可看到,如果仅仅只有一个特征进行分类,三角形和圆几乎是均匀分布在这条线段上,很难将10张照片线性分类。那么,增加一个特征后的情况会怎么样: + +![](./img/ch2/2.21.1.2.png) + +​ 图2.21.1.b 增加一个特征后,我们发现仍然无法找到一条直线将猫和狗分开。所以,考虑需要再增加一个特征: -![](./img/ch2/2-10.png) +![](./img/ch2/2.21.1.3.png) + +​ 图2.21.1.c -此时,我们终于找到了一个平面将猫和狗分开。需要注意的是,只有一个特征时,假设特征空间是长度为5的线段,则样本密度是10/5=2。有两个特征时,特征空间大小是5*5=25,样本密度是10/25=0.4。有三个特征时,特征空间大小是5*5*5=125,样本密度是10/125=0.08。如果继续增加特征数量,样本密度会更加稀疏,也就更容易找到一个超平面将训练样本分开。因为随着特征数量趋向于无限大,样本密度非常稀疏,训练样本被分错的可能性趋向于零。当我们将高维空间的分类结果映射到低维空间时,一个严重的问题出现了: +![](./img/ch2/2.21.1.4.png) -![](./img/ch2/2-11.png) +​ 图2.21.1.d -从图5可以看到将三维特征空间映射到二维特征空间后的结果。尽管在高维特征空间时训练样本线性可分,但是映射到低维空间后,结果正好相反。事实上,增加特征数量使得高维空间线性可分,相当于在低维空间内训练一个复杂的非线性分类器。不过,这个非线性分类器太过“聪明”,仅仅学到了一些特例。如果将其用来辨别那些未曾出现在训练样本中的测试样本时,通常结果不太理想。这其实就是我们在机器学习中学过的过拟合问题。 +​ 此时,可以找到一个平面将三角形和圆分开。 -![](./img/ch2/2-12.png) +​ 现在计算一下不同特征数是样本的密度: -尽管图6所示的只采用2个特征的线性分类器分错了一些训练样本,准确率似乎没有图4的高,但是,采用2个特征的线性分类器的泛化能力比采用3个特征的线性分类器要强。因为,采用2个特征的线性分类器学习到的不只是特例,而是一个整体趋势,对于那些未曾出现过的样本也可以比较好地辨别开来。换句话说,通过减少特征数量,可以避免出现过拟合问题,从而避免“维数灾难”。 +​ (1)一个特征时,假设特征空间时长度为5的线段,则样本密度为10/5=2。 -![](./img/ch2/2-13.png) +​ (2)两个特征时,特征空间大小为5*5=25,样本密度为10/25=0.4。 -图7从另一个角度诠释了“维数灾难”。假设只有一个特征时,特征的值域是0到1,每一只猫和狗的特征值都是唯一的。如果我们希望训练样本覆盖特征值值域的20%,那么就需要猫和狗总数的20%。我们增加一个特征后,为了继续覆盖特征值值域的20%就需要猫和狗总数的45%(0.45^2=0.2)。继续增加一个特征后,需要猫和狗总数的58%(0.58^3=0.2)。随着特征数量的增加,为了覆盖特征值值域的20%,就需要更多的训练样本。如果没有足够的训练样本,就可能会出现过拟合问题。 +​ (3)三个特征时,特征空间大小是5*5\*5=125,样本密度为10/125=0.08。 -![](./img/ch2/2-14.png) +​ 以此类推,如果继续增加特征数量,样本密度会越来越稀疏,此时,更容易找到一个超平面将训练样本分开。当特征数量增长至无限大时,样本密度就变得非常稀疏。 -通过上述例子,我们可以看到特征数量越多,训练样本就会越稀疏,分类器的参数估计就会越不准确,更加容易出现过拟合问题。“维数灾难”的另一个影响是训练样本的稀疏性并不是均匀分布的。处于中心位置的训练样本比四周的训练样本更加稀疏。 +​ 下面看一下将高维空间的分类结果映射到低维空间时,会出现什么情况? -假设有一个二维特征空间,如图8所示的矩形,在矩形内部有一个内切的圆形。由于越接近圆心的样本越稀疏,因此,相比于圆形内的样本,那些位于矩形四角的样本更加难以分类。那么,随着特征数量的增加,圆形的面积会不会变化呢?这里我们假设超立方体(hypercube)的边长d=1,那么计算半径为0.5的超球面(hypersphere)的体积(volume)的公式为: -$V(d)=\frac{\pi ^{\frac{d}{2}}}{\Gamma (\frac{d}{2}+1)}0.5^{d}$ +![](./img/ch2/2.21.1.5.png) -![](./img/ch2/2-15.png) +​ 图2.21.1.e -从图9可以看出随着特征数量的增加,超球面的体积逐渐减小直至趋向于零,然而超立方体的体积却不变。这个结果有点出乎意料,但部分说明了分类问题中的“维数灾难”:在高维特征空间中,大多数的训练样本位于超立方体的角落。 +​ 上图是将三维特征空间映射到二维特征空间后的结果。尽管在高维特征空间时训练样本线性可分,但是映射到低维空间后,结果正好相反。事实上,增加特征数量使得高维空间线性可分,相当于在低维空间内训练一个复杂的非线性分类器。不过,这个非线性分类器太过“聪明”,仅仅学到了一些特例。如果将其用来辨别那些未曾出现在训练样本中的测试样本时,通常结果不太理想,会造成过拟合问题。 -![](./img/ch2/2-16.png) +![](./img/ch2/2.21.1.6a.png) - 图10显示了不同维度下,样本的分布情况。在8维特征空间中,共有2^8=256个角落,而98%的样本分布在这些角落。随着维度的不断增加,公式2将趋向于0,其中dist_max和dist_min分别表示样本到中心的最大与最小距离。 +​ 图2.21.1.f -![](./img/ch2/2-17.png) +​ 上图所示的只采用2个特征的线性分类器分错了一些训练样本,准确率似乎没有图2.21.1.e的高,但是,采用2个特征的线性分类器的泛化能力比采用3个特征的线性分类器要强。因为,采用2个特征的线性分类器学习到的不只是特例,而是一个整体趋势,对于那些未曾出现过的样本也可以比较好地辨别开来。换句话说,通过减少特征数量,可以避免出现过拟合问题,从而避免“维数灾难”。 -因此,在高维特征空间中对于样本距离的度量失去意义。由于分类器基本都依赖于如Euclidean距离,Manhattan距离等,所以在特征数量过大时,分类器的性能就会出现下降。 +![](./img/ch2/2.21.1.6.png) -所以,我们如何避免“维数灾难”?图1显示了分类器的性能随着特征个数的变化不断增加,过了某一个值后,性能不升反降。这里的某一个值到底是多少呢?目前,还没有方法来确定分类问题中的这个阈值是多少,这依赖于训练样本的数量,决策边界的复杂性以及分类器的类型。理论上,如果训练样本的数量无限大,那么就不会存在“维数灾难”,我们可以采用任意多的特征来训练分类器。事实上,训练样本的数量是有限的,所以不应该采用过多的特征。此外,那些需要精确的非线性决策边界的分类器,比如neural network,knn,decision trees等的泛化能力往往并不是很好,更容易发生过拟合问题。因此,在设计这些分类器时应当慎重考虑特征的数量。相反,那些泛化能力较好的分类器,比如naive Bayesian,linear classifier等,可以适当增加特征的数量。 +​ 上从另一个角度诠释了“维数灾难”。假设只有一个特征时,特征的值域是0到1,每一个三角形和圆的特征值都是唯一的。如果我们希望训练样本覆盖特征值值域的20%,那么就需要三角形和圆总数的20%。我们增加一个特征后,为了继续覆盖特征值值域的20%就需要三角形和圆总数的45%(0.452=0.2)。继续增加一个特征后,需要三角形和圆总数的58%(0.583=0.2)。随着特征数量的增加,为了覆盖特征值值域的20%,就需要更多的训练样本。如果没有足够的训练样本,就可能会出现过拟合问题。 -如果给定了N个特征,我们该如何从中选出M个最优的特征?最简单粗暴的方法是尝试所有特征的组合,从中挑出M个最优的特征。事实上,这是非常花时间的,或者说不可行的。其实,已经有许多特征选择算法(feature selection algorithms)来帮助我们确定特征的数量以及选择特征。此外,还有许多特征抽取方法(feature extraction methods),比如PCA等。交叉验证(cross-validation)也常常被用于检测与避免过拟合问题。 +​ 通过上述例子,我们可以看到特征数量越多,训练样本就会越稀疏,分类器的参数估计就会越不准确,更加容易出现过拟合问题。“维数灾难”的另一个影响是训练样本的稀疏性并不是均匀分布的。处于中心位置的训练样本比四周的训练样本更加稀疏。 -参考资料: -[1] Vincent Spruyt. The Curse of Dimensionality in classification. Computer vision for dummies. 2014. [Link] +![](./img/ch2/2.21.1.7.png) + +​ 假设有一个二维特征空间,如图8所示的矩形,在矩形内部有一个内切的圆形。由于越接近圆心的样本越稀疏,因此,相比于圆形内的样本,那些位于矩形四角的样本更加难以分类。当维数变大时,特征超空间的容量不变,但单位圆的容量会趋于0,在高维空间中,大多数训练数据驻留在特征超空间的角落。散落在角落的数据要比处于中心的数据难于分类。 ### 2.21.2 怎样避免维数灾难 +**有待完善!!!** + 解决维度灾难问题: 主成分分析法PCA,线性判别法LDA @@ -1685,50 +2052,43 @@ Lassio缩减系数法、小波分析法、 ### 2.21.3 聚类和降维有什么区别与联系? -聚类用于找寻数据内在的分布结构,既可以作为一个单独的过程,比如异常检测等等。也可作为分类等其他学习任务的前驱过程。聚类是标准的无监督学习。 +​ 聚类用于找寻数据内在的分布结构,既可以作为一个单独的过程,比如异常检测等等。也可作为分类等其他学习任务的前驱过程。聚类是标准的无监督学习。 -1) 在一些推荐系统中需确定新用户的类型,但定义“用户类型”却可能不太容易,此时往往可先对原油的用户数据进行聚类,根据聚类结果将每个簇定义为一个类,然后再基于这些类训练分类模型,用于判别新用户的类型。 +​ 1) 在一些推荐系统中需确定新用户的类型,但定义“用户类型”却可能不太容易,此时往往可先对原油的用户数据进行聚类,根据聚类结果将每个簇定义为一个类,然后再基于这些类训练分类模型,用于判别新用户的类型。 -![](./img/ch2/2-18.jpg) +![](./img/ch2/2.21.3.1.png) -2)而降维则是为了缓解维数灾难的一个重要方法,就是通过某种数学变换将原始高维属性空间转变为一个低维“子空间”。其基于的假设就是,虽然人们平时观测到的数据样本虽然是高维的,但是实际上真正与学习任务相关的是个低维度的分布。从而通过最主要的几个特征维度就可以实现对数据的描述,对于后续的分类很有帮助。比如对于Kaggle上的泰坦尼克号生还问题。通过给定一个人的许多特征如年龄、姓名、性别、票价等,来判断其是否能在海难中生还。这就需要首先进行特征筛选,从而能够找出主要的特征,让学习到的模型有更好的泛化性。 +​ 2)而降维则是为了缓解维数灾难的一个重要方法,就是通过某种数学变换将原始高维属性空间转变为一个低维“子空间”。其基于的假设就是,虽然人们平时观测到的数据样本虽然是高维的,但是实际上真正与学习任务相关的是个低维度的分布。从而通过最主要的几个特征维度就可以实现对数据的描述,对于后续的分类很有帮助。比如对于Kaggle上的泰坦尼克号生还问题。通过给定一个人的许多特征如年龄、姓名、性别、票价等,来判断其是否能在海难中生还。这就需要首先进行特征筛选,从而能够找出主要的特征,让学习到的模型有更好的泛化性。 -聚类和降维都可以作为分类等问题的预处理步骤。 +​ 聚类和降维都可以作为分类等问题的预处理步骤。 ![](./img/ch2/2-19.jpg) -但是他们虽然都能实现对数据的约减。但是二者适用的对象不同,聚类针对的是数据点,而降维则是对于数据的特征。另外它们着很多种实现方法。聚类中常用的有K-means、层次聚类、基于密度的聚类等;降维中常用的则PCA、Isomap、LLE等。 +​ 但是他们虽然都能实现对数据的约减。但是二者适用的对象不同,聚类针对的是数据点,而降维则是对于数据的特征。另外它们着很多种实现方法。聚类中常用的有K-means、层次聚类、基于密度的聚类等;降维中常用的则PCA、Isomap、LLE等。 -### 2.21.4 四种聚类方法之比较 -http://www.cnblogs.com/William_Fire/archive/2013/02/09/2909499.html - 聚类分析是一种重要的人类行为,早在孩提时代,一个人就通过不断改进下意识中的聚类模式来学会如何区分猫狗、动物植物。目前在许多领域都得到了广泛的研究和成功的应用,如用于模式识别、数据分析、图像处理、市场研究、客户分割、Web文档分类等[1]。 -聚类就是按照某个特定标准(如距离准则)把一个数据集分割成不同的类或簇,使得同一个簇内的数据对象的相似性尽可能大,同时不在同一个簇中的数据对象的差异性也尽可能地大。即聚类后同一类的数据尽可能聚集到一起,不同数据尽量分离。 -聚类技术[2]正在蓬勃发展,对此有贡献的研究领域包括数据挖掘、统计学、机器学习、空间数据库技术、生物学以及市场营销等。各种聚类方法也被不断提出和改进,而不同的方法适合于不同类型的数据,因此对各种聚类方法、聚类效果的比较成为值得研究的课题。 +### 2.21.4 四种聚类方法之比较 -1 聚类算法的分类 +http://www.cnblogs.com/William_Fire/archive/2013/02/09/2909499.html -目前,有大量的聚类算法[3]。而对于具体应用,聚类算法的选择取决于数据的类型、聚类的目的。如果聚类分析被用作描述或探查的工具,可以对同样的数据尝试多种算法,以发现数据可能揭示的结果。 -​ -主要的聚类算法可以划分为如下几类:划分方法、层次方法、基于密度的方法、基于网格的方法以及基于模型的方法[4-6]。 -每一类中都存在着得到广泛应用的算法,例如:划分方法中的k-means[7]聚类算法、层次方法中的凝聚型层次聚类算法[8]、基于模型方法中的神经网络[9]聚类算法等。 -​ 目前,聚类问题的研究不仅仅局限于上述的硬聚类,即每一个数据只能被归为一类,模糊聚类[10]也是聚类分析中研究较为广泛的一个分支。模糊聚类通过隶 属函数来确定每个数据隶属于各个簇的程度,而不是将一个数据对象硬性地归类到某一簇中。目前已有很多关于模糊聚类的算法被提出,如著名的FCM算法等。 -​ 本文主要对k-means聚类算法、凝聚型层次聚类算法、神经网络聚类算法之SOM,以及模糊聚类的FCM算法通过通用测试数据集进行聚类效果的比较和分析。 -2 四种常用聚类算法研究 +​ 聚类就是按照某个特定标准(如距离准则)把一个数据集分割成不同的类或簇,使得同一个簇内的数据对象的相似性尽可能大,同时不在同一个簇中的数据对象的差异性也尽可能地大。即聚类后同一类的数据尽可能聚集到一起,不同数据尽量分离。 +​ 主要的聚类算法可以划分为如下几类:划分方法、层次方法、基于密度的方法、基于网格的方法以及基于模型的方法。下面主要对k-means聚类算法、凝聚型层次聚类算法、神经网络聚类算法之SOM,以及模糊聚类的FCM算法通过通用测试数据集进行聚类效果的比较和分析。 -2.1 k-means聚类算法 +### 2.21.5 k-means聚类算法 k-means是划分方法中较经典的聚类算法之一。由于该算法的效率高,所以在对大规模数据进行聚类时被广泛应用。目前,许多算法均围绕着该算法进行扩展和改进。 k-means算法以k为参数,把n个对象分成k个簇,使簇内具有较高的相似度,而簇间的相似度较低。k-means算法的处理过程如下:首先,随机地 选择k个对象,每个对象初始地代表了一个簇的平均值或中心;对剩余的每个对象,根据其与各簇中心的距离,将它赋给最近的簇;然后重新计算每个簇的平均值。 这个过程不断重复,直到准则函数收敛。通常,采用平方误差准则,其定义如下: -  $E=\sum_{i=1}^{k}\sum_{p\subset C}|p-m_{i}|^{2}$ +  $E=\sum_{i=1}^{k}\sum_{p\subset C}|p-m_{i}|^{2}​$ - 这里E是数据库中所有对象的平方误差的总和,p是空间中的点,mi是簇Ci的平均值[9]。该目标函数使生成的簇尽可能紧凑独立,使用的距离度量是欧几里得距离,当然也可以用其他距离度量。k-means聚类算法的算法流程如下: + 这里E是数据库中所有对象的平方误差的总和,p是空间中的点,mi是簇Ci的平均值[9]。该目标函数使生成的簇尽可能紧凑独立,使用的距离度量是欧几里得距离,当然也可以用其他距离度量。 + +k-means聚类算法的算法流程如下: ​ 输入:包含n个对象的数据库和簇的数目k; ​ 输出:k个簇,使平方误差准则最小。 ​ 步骤: @@ -1738,7 +2098,8 @@ http://www.cnblogs.com/William_Fire/archive/2013/02/09/2909499.html   (4) 更新簇的平均值,即计算每个簇中对象的平均值;   (5) until不再发生变化。 -2.2 层次聚类算法 +### 2.21.6 层次聚类算法 + ​ 根据层次分解的顺序是自底向上的还是自上向下的,层次聚类算法分为凝聚的层次聚类算法和分裂的层次聚类算法。  凝聚型层次聚类的策略是先将每个对象作为一个簇,然后合并这些原子簇为越来越大的簇,直到所有对象都在一个簇中,或者某个终结条件被满足。绝大多数层次聚类属于凝聚型层次聚类,它们只是在簇间相似度的定义上有所不同。四种广泛采用的簇间距离度量方法如下: @@ -1751,24 +2112,24 @@ http://www.cnblogs.com/William_Fire/archive/2013/02/09/2909499.html  (3) 重新计算新类与所有类之间的距离;  (4) 重复(2)、(3),直到所有类最后合并成一类。 -### 2.21.5 SOM聚类算法 -SOM神经网络[11]是由芬兰神经网络专家Kohonen教授提出的,该算法假设在输入对象中存在一些拓扑结构或顺序,可以实现从输入空间(n维)到输出平面(2维)的降维映射,其映射具有拓扑特征保持性质,与实际的大脑处理有很强的理论联系。 +### 2.21.7 SOM聚类算法 +​ SOM神经网络[11]是由芬兰神经网络专家Kohonen教授提出的,该算法假设在输入对象中存在一些拓扑结构或顺序,可以实现从输入空间(n维)到输出平面(2维)的降维映射,其映射具有拓扑特征保持性质,与实际的大脑处理有很强的理论联系。 -SOM网络包含输入层和输出层。输入层对应一个高维的输入向量,输出层由一系列组织在2维网格上的有序节点构成,输入节点与输出节点通过权重向量连接。 学习过程中,找到与之距离最短的输出层单元,即获胜单元,对其更新。同时,将邻近区域的权值更新,使输出节点保持输入向量的拓扑特征。 +​ SOM网络包含输入层和输出层。输入层对应一个高维的输入向量,输出层由一系列组织在2维网格上的有序节点构成,输入节点与输出节点通过权重向量连接。 学习过程中,找到与之距离最短的输出层单元,即获胜单元,对其更新。同时,将邻近区域的权值更新,使输出节点保持输入向量的拓扑特征。 算法流程: -(1) 网络初始化,对输出层每个节点权重赋初值; -(2) 将输入样本中随机选取输入向量,找到与输入向量距离最小的权重向量; -(3) 定义获胜单元,在获胜单元的邻近区域调整权重使其向输入向量靠拢; -(4) 提供新样本、进行训练; -(5) 收缩邻域半径、减小学习率、重复,直到小于允许值,输出聚类结果。 +​ (1) 网络初始化,对输出层每个节点权重赋初值; +​ (2) 将输入样本中随机选取输入向量,找到与输入向量距离最小的权重向量; +​ (3) 定义获胜单元,在获胜单元的邻近区域调整权重使其向输入向量靠拢; +​ (4) 提供新样本、进行训练; +​ (5) 收缩邻域半径、减小学习率、重复,直到小于允许值,输出聚类结果。 -### 2.21.6 FCM聚类算法 +### 2.21.8 FCM聚类算法 -1965年美国加州大学柏克莱分校的扎德教授第一次提出了‘集合’的概念。经过十多年的发展,模糊集合理论渐渐被应用到各个实际应用方面。为克服非此即彼的分类缺点,出现了以模糊集合论为数学基础的聚类分析。用模糊数学的方法进行聚类分析,就是模糊聚类分析[12]。 +​ 1965年美国加州大学柏克莱分校的扎德教授第一次提出了‘集合’的概念。经过十多年的发展,模糊集合理论渐渐被应用到各个实际应用方面。为克服非此即彼的分类缺点,出现了以模糊集合论为数学基础的聚类分析。用模糊数学的方法进行聚类分析,就是模糊聚类分析[12]。 -FCM算法是一种以隶属度来确定每个数据点属于某个聚类程度的算法。该聚类算法是传统硬聚类算法的一种改进。 +​ FCM算法是一种以隶属度来确定每个数据点属于某个聚类程度的算法。该聚类算法是传统硬聚类算法的一种改进。 ![](./img/ch2/2-21.gif) @@ -1800,7 +2161,7 @@ FCM算法是一种以隶属度来确定每个数据点属于某个聚类程度 (3)平均准确度:设原数据集有k个类,用ci表示第i类,ni为ci中样本的个数,mi为聚类正确的个数,则mi/ni为 第i类中的精度,则平均精度为: -$avg=\frac{1}{k}\sum_{i=1}^{k}\frac{m_{i}}{n_{i}}$ +$avg=\frac{1}{k}\sum_{i=1}^{k}\frac{m_{i}}{n_{i}}​$ ## 2.22 GBDT和随机森林的区别 @@ -1818,7 +2179,7 @@ GBDT和随机森林的不同点: ## 2.23 大数据与深度学习之间的关系 -大数据**通常被定义为“超出常用软件工具捕获,管理和处理能力”的数据集。 +**大数据**通常被定义为“超出常用软件工具捕获,管理和处理能力”的数据集。 **机器学习**关心的问题是如何构建计算机程序使用经验自动改进。 **数据挖掘**是从数据中提取模式的特定算法的应用。 在数据挖掘中,重点在于算法的应用,而不是算法本身。 diff --git "a/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/\347\254\254\344\272\214\347\253\240_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200.pdf" "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/\347\254\254\344\272\214\347\253\240_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200.pdf" new file mode 100644 index 00000000..7f78c7fb Binary files /dev/null and "b/ch02_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200/\347\254\254\344\272\214\347\253\240_\346\234\272\345\231\250\345\255\246\344\271\240\345\237\272\347\241\200.pdf" differ diff --git "a/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.1.1.5.png" "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.1.1.5.png" new file mode 100644 index 00000000..dde211ce Binary files /dev/null and "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.1.1.5.png" differ diff --git "a/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.1.1.6.png" "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.1.1.6.png" new file mode 100644 index 00000000..1bd76971 Binary files /dev/null and "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.1.1.6.png" differ diff --git "a/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.1.6.1.png" "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.1.6.1.png" new file mode 100644 index 00000000..e0ce77d9 Binary files /dev/null and "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.1.6.1.png" differ diff --git "a/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.12.2.1.png" "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.12.2.1.png" new file mode 100644 index 00000000..34f2d8b6 Binary files /dev/null and "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.12.2.1.png" differ diff --git "a/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.12.2.2.png" "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.12.2.2.png" new file mode 100644 index 00000000..ad3d4bd6 Binary files /dev/null and "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.12.2.2.png" differ diff --git "a/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.1.1.png" "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.1.1.png" new file mode 100644 index 00000000..160cf461 Binary files /dev/null and "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.1.1.png" differ diff --git "a/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.1.2.png" "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.1.2.png" new file mode 100644 index 00000000..fec7b5b1 Binary files /dev/null and "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.1.2.png" differ diff --git "a/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.2.1.png" "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.2.1.png" new file mode 100644 index 00000000..02dbca08 Binary files /dev/null and "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.2.1.png" differ diff --git "a/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.3.1.png" "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.3.1.png" new file mode 100644 index 00000000..1c4dacd9 Binary files /dev/null and "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.3.1.png" differ diff --git "a/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.3.2.png" "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.3.2.png" new file mode 100644 index 00000000..09f4d9e2 Binary files /dev/null and "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.3.2.png" differ diff --git "a/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.3.4.png" "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.3.4.png" new file mode 100644 index 00000000..03f1c6a9 Binary files /dev/null and "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.3.4.png" differ diff --git "a/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.3.5.png" "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.3.5.png" new file mode 100644 index 00000000..56443fd2 Binary files /dev/null and "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.3.5.png" differ diff --git "a/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.3.6.png" "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.3.6.png" new file mode 100644 index 00000000..bda9c5cb Binary files /dev/null and "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.3.6.png" differ diff --git "a/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.4.1.png" "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.4.1.png" new file mode 100644 index 00000000..f91e8ab4 Binary files /dev/null and "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.4.1.png" differ diff --git "a/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.5.1.png" "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.5.1.png" new file mode 100644 index 00000000..1236163e Binary files /dev/null and "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.5.1.png" differ diff --git "a/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.5.2.png" "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.5.2.png" new file mode 100644 index 00000000..c36f3bfd Binary files /dev/null and "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.5.2.png" differ diff --git "a/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.5.3.png" "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.5.3.png" new file mode 100644 index 00000000..d53c8ea8 Binary files /dev/null and "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.5.3.png" differ diff --git "a/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.5.4.png" "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.5.4.png" new file mode 100644 index 00000000..f00cca44 Binary files /dev/null and "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.2.5.4.png" differ diff --git "a/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.4.9.1.png" "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.4.9.1.png" new file mode 100644 index 00000000..3e126ba7 Binary files /dev/null and "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.4.9.1.png" differ diff --git "a/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.4.9.2.png" "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.4.9.2.png" new file mode 100644 index 00000000..ea9b0c34 Binary files /dev/null and "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.4.9.2.png" differ diff --git "a/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.4.9.3.png" "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.4.9.3.png" new file mode 100644 index 00000000..fe1d7779 Binary files /dev/null and "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.4.9.3.png" differ diff --git "a/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.6.3.1.png" "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.6.3.1.png" new file mode 100644 index 00000000..d091389e Binary files /dev/null and "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.6.3.1.png" differ diff --git "a/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.6.7.1.png" "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.6.7.1.png" new file mode 100644 index 00000000..4b98c00e Binary files /dev/null and "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.6.7.1.png" differ diff --git "a/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.8.2.1.png" "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.8.2.1.png" new file mode 100644 index 00000000..1236163e Binary files /dev/null and "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/img/ch3/3.8.2.1.png" differ diff --git "a/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/\347\254\254\344\270\211\347\253\240_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200.md" "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/\347\254\254\344\270\211\347\253\240_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200.md" index 9f38cd51..fbb3c4c0 100644 --- "a/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/\347\254\254\344\270\211\347\253\240_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200.md" +++ "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/\347\254\254\344\270\211\347\253\240_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200.md" @@ -6,93 +6,74 @@ ### 3.1.1 神经网络组成? -为了描述神经网络,我们先从最简单的神经网络说起。 +神经网络类型众多,其中最为重要的是多层感知机。为了详细地描述神经网络,我们先从最简单的神经网络说起。 **感知机** +多层感知机中的特征神经元模型称为感知机,由*Frank Rosenblatt*于1957年发明。 + 简单的感知机如下图所示: ![](./img/ch3/3-1.png) -其输出为: +其中$x_1$,$x_2$,$x_3$为感知机的输入,其输出为: $$ output = \left\{ \begin{aligned} -0, \quad if \sum_i w_i x_i \le threshold \\ -1, \quad if \sum_i w_i x_i > threshold +0, \quad if \ \ \sum_i w_i x_i \le threshold \\ +1, \quad if \ \ \sum_i w_i x_i > threshold \end{aligned} \right. $$ -假如把感知机想象成一个加权投票机制,比如 3 位评委给一个歌手打分,打分分别为 4 分、1 分、-3 分,这 3 位评分的权重分别是 1、3、2,则该歌手最终得分为 $ 4 * 1 + 1 * 3 + (-3) * 2 = 1 $。按照比赛规则,选取的 threshold 为 3,说明只有歌手的综合评分大于 3 时,才可顺利晋级。对照感知机,该选手被淘汰,因为 +假如把感知机想象成一个加权投票机制,比如 3 位评委给一个歌手打分,打分分别为$ 4 $分、$1$ 分、$-3 $分,这$ 3$ 位评分的权重分别是 $1、3、2$,则该歌手最终得分为 $4 * 1 + 1 * 3 + (-3) * 2 = 1$ 。按照比赛规则,选取的 $threshold$ 为 $3$,说明只有歌手的综合评分大于$ 3$ 时,才可顺利晋级。对照感知机,该选手被淘汰,因为 $$ \sum_i w_i x_i < threshold=3, output = 0 $$ -用 $ -b $ 代替 threshold。输出变为: +用 $-b$ 代替 $threshold$,输出变为: $$ output = \left\{ \begin{aligned} -0, \quad if w \cdot x + b \le 0 \\ -1, \quad if w \cdot x + b > 0 +0, \quad if \ \ w \cdot x + b \le threshold \\ +1, \quad if \ \ w \cdot x + b > threshold \end{aligned} \right. $$ -设置合适的 $ x $ 和 $ b $,一个简单的感知机单元的与非门表示如下: +设置合适的 $x$ 和 $b$ ,一个简单的感知机单元的与非门表示如下: ![](./img/ch3/3-2.png) -当输入为 $ 0,1 $ 时,感知机输出为 $ 0 * (-2) + 1 * (-2) + 3 = 1 $。 +当输入为 $0$,$1$ 时,感知机输出为 $ 0 * (-2) + 1 * (-2) + 3 = 1$。 复杂一些的感知机由简单的感知机单元组合而成: ![](./img/ch3/3-3.png) -**Sigmoid单元** - -感知机单元的输出只有 0 和 1,实际情况中,更多的输出类别不止 0 和 1,而是 $ [0, 1] $ 上的概率值,这时候就需要 sigmoid 函数把任意实数映射到 $ [0, 1] $ 上。 - -神经元的输入 - -$$ -z = \sum_i w_i x_i + b -$$ +**多层感知机** -假设神经元的输出采用 sigmoid 激活函数 +多层感知机由感知机推广而来,最主要的特点是有多个神经元层,因此也叫深度神经网络。相比于单独的感知机,多层感知机的第 $ i ​$ 层的每个神经元和第 $ i-1 ​$ 层的每个神经元都有连接。 -$$ -\sigma(z) = \frac{1}{1+e^{-z}} -$$ +![](./img/ch3/3.1.1.5.png) -sigmoid 激活函数图像如下图所示: +输出层可以不止有$ 1​$ 个神经元。隐藏层可以只有$ 1​$ 层,也可以有多层。输出层为多个神经元的神经网络例如下图: -![](./img/ch3/3-4.png) +![](./img/ch3/3.1.1.6.png) -全连接神经网络 -即第 $ i $ 层的每个神经元和第 $ i-1 $ 层的每个神经元都有连接。 -![](./img/ch3/3-5.png) - -输出层可以不止有 1 个神经元。隐藏层可以只有 1 层,也可以有多层。输出层为多个神经元的神经网络例如下图: - -![](./img/ch3/3-6.png) - - -### 3.1.2神经网络有哪些常用模型结构? - -答案来源:[25张图让你读懂神经网络架构](https://blog.csdn.net/nicholas_liu2017/article/details/73694666) +### 3.1.2 神经网络有哪些常用模型结构? 下图包含了大部分常用的模型: ![](./img/ch3/3-7.jpg) -### 3.1.3如何选择深度学习开发平台? +### 3.1.3 如何选择深度学习开发平台? -现有的深度学习开源平台主要有 Caffe, Torch, MXNet, CNTK, Theano, TensorFlow, Keras 等。那如何选择一个适合自己的平台呢,下面列出一些衡量做参考。 +现有的深度学习开源平台主要有 Caffe, PyTorch, MXNet, CNTK, Theano, TensorFlow, Keras 等。那如何选择一个适合自己的平台呢,下面列出一些衡量做参考。 **参考1:与现有编程平台、技能整合的难易程度** @@ -100,7 +81,7 @@ sigmoid 激活函数图像如下图所示: **参考2: 与相关机器学习、数据处理生态整合的紧密程度** -深度学习研究离不开各种数据处理、可视化、统计推断等软件包。考虑建模之前,是否具有方便的数据预处理工具?建模之后,是否具有方便的工具进行可视化、统计推断、数据分析? +深度学习研究离不开各种数据处理、可视化、统计推断等软件包。考虑建模之前,是否具有方便的数据预处理工具?建模之后,是否具有方便的工具进行可视化、统计推断、数据分析。 **参考3:对数据量及硬件的要求和支持** @@ -114,32 +95,25 @@ sigmoid 激活函数图像如下图所示: 有些平台是专门为深度学习研究和应用进行开发的,有些平台对分布式计算、GPU 等构架都有强大的优化,能否用这些平台/软件做其他事情?比如有些深度学习软件是可以用来求解二次型优化;有些深度学习平台很容易被扩展,被运用在强化学习的应用中。 -### 3.1.4为什么使用深层表示? - -1. 深度神经网络的多层隐藏层中,前几层能学习一些低层次的简单特征,后几层能把前面简单的特征结合起来,去学习更加复杂的东西。比如刚开始检测到的是边缘信息,而后检测更为细节的信息。 +### 3.1.4 为什么使用深层表示? +1. 深度神经网络是一种特征递进式的学习算法,浅层的神经元直接从输入数据中学习一些低层次的简单特征,例如边缘、纹理等。而深层的特征则基于已学习到的浅层特征继续学习更高级的特征,从计算机的角度学习深层的语义信息。 2. 深层的网络隐藏单元数量相对较少,隐藏层数目较多,如果浅层的网络想要达到同样的计算结果则需要指数级增长的单元数量才能达到。 -### 3.1.5为什么深层神经网络难以训练? - -答案来源: +### 3.1.5 为什么深层神经网络难以训练? -[为什么深层神经网络难以训练](https://blog.csdn.net/BinChasing/article/details/50300069) -[为什么很难训练深度神经网络](http://mini.eastday.com/mobile/180116023302833.html) +1. 梯度消失($Vanishing$ $Gradient$) + 梯度消失是指通过隐藏层从后向前看,梯度会变的越来越小,说明前面层的学习会显著慢于后面层的学习,所以学习会卡住,除非梯度变大。 - -1. 梯度消失 - 梯度消失是指通过隐藏层从后向前看,梯度会变的越来越小,说明前面层的学习会显著慢于后面层的学习,所以学习会卡住,除非梯度变大。下图是不同隐含层的学习速率; + 梯度消失的原因受到多种因素影响,例如学习率的大小,网络参数的初始化,激活函数的边缘效应等。在深层神经网络中,每一个神经元计算得到的梯度都会传递给前一层,较浅层的神经元接收到的梯度受到之前所有层梯度的影响。如果计算得到的梯度值非常小,随着层数增多,求出的梯度更新信息将会以指数形式衰减,就会发生梯度消失。下图是不同隐含层的学习速率: ![](./img/ch3/3-8.png) -2. 梯度爆炸 - 又称exploding gradient problem,在深度网络或循环神经网络(RNN)等网络结构中,梯度可在网络更新的过程中不断累积,变成非常大的梯度,导致网络权重值的大幅更新,使得网络不稳定;在极端情况下,权重值甚至会溢出,变为NaN值,再也无法更新。 具体可参考文献:[A Gentle Introduction to Exploding Gradients in Neural Networks](https://machinelearningmastery.com/exploding-gradients-in-neural-networks/) - -3. 权重矩阵的退化导致模型的有效自由度减少。参数空间中学习的退化速度减慢,导致减少了模型的有效维数,网络的可用自由度对学习中梯度范数的贡献不均衡,随着相乘矩阵的数量(即网络深度)的增加,矩阵的乘积变得越来越退化; +2. 梯度爆炸($Exploding$ $Gradient $) + 在深度网络或循环神经网络($Recurrent$ $Neural$ $Network$, $RNN$)等网络结构中,梯度可在网络更新的过程中不断累积,变成非常大的梯度,导致网络权重值的大幅更新,使得网络不稳定;在极端情况下,权重值甚至会溢出,变为$NaN$值,再也无法更新。 -在有硬饱和边界的非线性网络中(例如 ReLU 网络),随着深度增加,退化过程会变得越来越快。Duvenaud 等人 2014 年的论文里展示了关于该退化过程的可视化: +3. 权重矩阵的退化导致模型的有效自由度减少。参数空间中学习的退化速度减慢,导致减少了模型的有效维数,网络的可用自由度对学习中梯度范数的贡献不均衡,随着相乘矩阵的数量(即网络深度)的增加,矩阵的乘积变得越来越退化。在有硬饱和边界的非线性网络中(例如 $ReLU $网络),随着深度增加,退化过程会变得越来越快。$Duvenaud$ 等人 $2014 $年的论文里展示了关于该退化过程的可视化: ![](./img/ch3/3-9.jpg) @@ -147,11 +121,15 @@ sigmoid 激活函数图像如下图所示: ### 3.1.6 深度学习和机器学习有什么不同? -机器学习:利用计算机、概率论、统计学等知识,输入数据,让计算机学会新知识。机器学习的过程,就是通过训练数据寻找目标函数。 +机器学习:利用计算机、概率论、统计学等知识,输入数据,让计算机学会新知识。机器学习的过程,就是训练数据去优化目标函数。 + +深度学习:是一种特殊的机器学习,具有强大的能力和灵活性。它通过学习将世界表示为嵌套的概念层次结构,每个概念都与更简单的概念相关,而抽象的概念则用于计算更抽象的表示。 + +传统的机器学习需要定义一些手工特征,从而有目的的去提取目标信息, 非常依赖任务的特异性以及设计特征的专家经验。而深度学习可以从大数据中先学习简单的特征,并从其逐渐学习到更为复杂抽象的深层特征,不依赖人工的特征工程,这也是深度学习在大数据时代受欢迎的一大原因。 -深度学习是机器学习的一种,现在深度学习比较火爆。在传统机器学习中,手工设计特征对学习效果很重要,但是特征工程非常繁琐。而深度学习能够从大数据中自动学习特征,这也是深度学习在大数据时代受欢迎的一大原因。 -![](./img/ch3/3-10.jpg) + +![](./img/ch3/3.1.6.1.png) ![](./img/ch3/3-11.jpg) @@ -159,63 +137,57 @@ sigmoid 激活函数图像如下图所示: ### 3.2.1前向传播与反向传播? -答案来源:[神经网络中前向传播和反向传播解析](https://blog.csdn.net/lhanchao/article/details/51419150) - -在神经网络的计算中,主要由前向传播(foward propagation,FP)和反向传播(backward propagation,BP)。 +神经网络的计算主要有两种:前向传播($foward​$ $propagation​$,$FP​$)作用于每一层的输入,通过逐层计算得到输出结果;反向传播($backward​$ $propagation​$,$BP​$)作用于网络的输出,通过计算梯度由深到浅更新网络参数。 **前向传播** -![](./img/ch3/3-12.png) +![](./img/ch3/3.2.1.1.png) -假设上一层结点 $ i,j,k,... $ 等一些结点与本层的结点 $ w $ 有连接,那么结点 $ w $ 的值怎么算呢?就是通过上一层的 $ i,j,k,... $ 等结点以及对应的连接权值进行加权和运算,最终结果再加上一个偏置项(图中为了简单省略了),最后在通过一个非线性函数(即激活函数),如 ReLu,sigmoid 等函数,最后得到的结果就是本层结点 $ w $ 的输出。 +假设上一层结点 $ i,j,k,... ​$ 等一些结点与本层的结点 $ w ​$ 有连接,那么结点 $ w ​$ 的值怎么算呢?就是通过上一层的 $ i,j,k,... ​$ 等结点以及对应的连接权值进行加权和运算,最终结果再加上一个偏置项(图中为了简单省略了),最后在通过一个非线性函数(即激活函数),如 $ReLu​$,$sigmoid​$ 等函数,最后得到的结果就是本层结点 $ w ​$ 的输出。 最终不断的通过这种方法一层层的运算,得到输出层结果。 **反向传播** -![](./img/ch3/3-13.png) +![](./img/ch3/3.2.1.2.png) 由于我们前向传播最终得到的结果,以分类为例,最终总是有误差的,那么怎么减少误差呢,当前应用广泛的一个算法就是梯度下降算法,但是求梯度就要求偏导数,下面以图中字母为例讲解一下: -设最终中误差为 $ E $,对于输出那么 $ E $ 对于输出节点 $ y_l $ 的偏导数是 $ y_l - t_l $,其中 $ t_l $ 是真实值,$ \frac{\partial y_l}{\partial z_l} $ 是指上面提到的激活函数,$ z_l $ 是上面提到的加权和,那么这一层的 $ E $ 对于 $ z_l $ 的偏导数为 $ \frac{\partial E}{\partial z_l} = \frac{\partial E}{\partial y_l} \frac{\partial y_l}{\partial z_l} $。同理,下一层也是这么计算,只不过 $ \frac{\partial E}{\partial y_k} $ 计算方法变了,一直反向传播到输入层,最后有 $ \frac{\partial E}{\partial x_i} = \frac{\partial E}{\partial y_j} \frac{\partial y_j}{\partial z_j} $,且 $ \frac{\partial z_j}{\partial x_i} = w_i j $。然后调整这些过程中的权值,再不断进行前向传播和反向传播的过程,最终得到一个比较好的结果; +设最终误差为 $ E $且输出层的激活函数为线性激活函数,对于输出那么 $ E $ 对于输出节点 $ y_l $ 的偏导数是 $ y_l - t_l $,其中 $ t_l $ 是真实值,$ \frac{\partial y_l}{\partial z_l} $ 是指上面提到的激活函数,$ z_l $ 是上面提到的加权和,那么这一层的 $ E $ 对于 $ z_l $ 的偏导数为 $ \frac{\partial E}{\partial z_l} = \frac{\partial E}{\partial y_l} \frac{\partial y_l}{\partial z_l} $。同理,下一层也是这么计算,只不过 $ \frac{\partial E}{\partial y_k} $ 计算方法变了,一直反向传播到输入层,最后有 $ \frac{\partial E}{\partial x_i} = \frac{\partial E}{\partial y_j} \frac{\partial y_j}{\partial z_j} $,且 $ \frac{\partial z_j}{\partial x_i} = w_i j ​$。然后调整这些过程中的权值,再不断进行前向传播和反向传播的过程,最终得到一个比较好的结果。 ### 3.2.2如何计算神经网络的输出? -答案来源:[零基础入门深度学习(3) - 神经网络和反向传播算法](https://www.zybuluo.com/hanbingtao/note/476663) - -![](./img/ch3/3-14.png) +![](./img/ch3/3.2.2.1.png) -如上图,输入层有三个节点,我们将其依次编号为 1、2、3;隐藏层的 4 个节点,编号依次为 4、5、6、7;最后输出层的两个节点编号为 8、9。比如,隐藏层的节点 4,它和输入层的三个节点 1、2、3 之间都有连接,其连接上的权重分别为是 $ w_{41}, w_{42}, w_{43} $。 +如上图,输入层有三个节点,我们将其依次编号为 1、2、3;隐藏层的 4 个节点,编号依次为 4、5、6、7;最后输出层的两个节点编号为 8、9。比如,隐藏层的节点 4,它和输入层的三个节点 1、2、3 之间都有连接,其连接上的权重分别为是 $ w_{41}, w_{42}, w_{43} ​$。 为了计算节点 4 的输出值,我们必须先得到其所有上游节点(也就是节点 1、2、3)的输出值。节点 1、2、3 是输入层的节点,所以,他们的输出值就是输入向量本身。按照上图画出的对应关系,可以看到节点 1、2、3 的输出值分别是 $ x_1, x_2, x_3 $。 $$ -a_4 = \sigma(w^T \cdot a) = \sigma(w_{41}x_4 + w_{42}x_2 + w_{43}x_3 + w_{4b}) +a_4 = \sigma(w^T \cdot a) = \sigma(w_{41}x_4 + w_{42}x_2 + w_{43}a_3 + w_{4b}) $$ -其中 $ w_{4b} $ 是节点 4 的偏置项 +其中 $ w_{4b} $ 是节点 4 的偏置项。 同样,我们可以继续计算出节点 5、6、7 的输出值 $ a_5, a_6, a_7 $。 -计算输出层的节点 8 的输出值 $ y_1 $: +计算输出层的节点 8 的输出值 $ y_1 ​$: $$ y_1 = \sigma(w^T \cdot a) = \sigma(w_{84}a_4 + w_{85}a_5 + w_{86}a_6 + w_{87}a_7 + w_{8b}) $$ -其中 $ w_{8b} $ 是节点 8 的偏置项。 +其中 $ w_{8b} ​$ 是节点 8 的偏置项。 -同理,我们还可以计算出 $ y_2 $。这样输出层所有节点的输出值计算完毕,我们就得到了在输入向量 $ x_1, x_2, x_3, x_4 $ 时,神经网络的输出向量 $ y_1, y_2 ​$ 。这里我们也看到,输出向量的维度和输出层神经元个数相同。 +同理,我们还可以计算出 $ y_2 $。这样输出层所有节点的输出值计算完毕,我们就得到了在输入向量 $ x_1, x_2, x_3, x_4 $ 时,神经网络的输出向量 $ y_1, y_2 $ 。这里我们也看到,输出向量的维度和输出层神经元个数相同。 ### 3.2.3如何计算卷积神经网络输出值? -答案来源:[零基础入门深度学习(4) - 卷积神经网络](https://www.zybuluo.com/hanbingtao/note/485480) - 假设有一个 5\*5 的图像,使用一个 3\*3 的 filter 进行卷积,想得到一个 3\*3 的 Feature Map,如下所示: -![](./img/ch3/3-15.png) +![](./img/ch3/3.2.3.1.png) -$ x_{i,j} $ 表示图像第 $ i $ 行第 $ j $ 列元素。$ w_{m,n} $ 表示 filter 第 $ m $ 行第 $ n $ 列权重。 $ w_b $ 表示 filter 的偏置项。 表示 feature map 第 $ i $ 行第 $ j $ 列元素。 $ f $ 表示激活函数,这里以 relu 函数为例。 +$ x_{i,j} $ 表示图像第 $ i $ 行第 $ j $ 列元素。$ w_{m,n} $ 表示 filter​ 第 $ m $ 行第 $ n $ 列权重。 $ w_b $ 表示 $filter$ 的偏置项。 表$a_i,_j$示 feature map 第 $ i$ 行第 $ j $ 列元素。 $f$ 表示激活函数,这里以$ ReLU$ 函数为例。 卷积计算公式如下: @@ -223,45 +195,40 @@ $$ a_{i,j} = f(\sum_{m=0}^2 \sum_{n=0}^2 w_{m,n} x_{i+m, j+n} + w_b ) $$ -当步长为 1 时,计算 feature map 元素 $ a_{0,0} $ 如下: +当步长为 $1$ 时,计算 feature​ map​ 元素 $ a_{0,0} $ 如下: $$ a_{0,0} = f(\sum_{m=0}^2 \sum_{n=0}^2 w_{m,n} x_{0+m, 0+n} + w_b ) -= relu(w_{0,0} x_{0,0} + w_{0,1} x_{0,1} + w_{0,2} x_{0,2} + w_{1,0} x_{1,0} + w_{1,1} x_{1,1} + w_{1,2} x_{1,2} + w_{2,0} x_{2,0} + w_{2,1} x_{2,1} + w_{2,2} x_{2,2}) \\ += relu(w_{0,0} x_{0,0} + w_{0,1} x_{0,1} + w_{0,2} x_{0,2} + w_{1,0} x_{1,0} + \\w_{1,1} x_{1,1} + w_{1,2} x_{1,2} + w_{2,0} x_{2,0} + w_{2,1} x_{2,1} + w_{2,2} x_{2,2}) \\ = 1 + 0 + 1 + 0 + 1 + 0 + 0 + 0 + 1 \\ - = 4 $$ -结果如下: - -![](./img/ch3/3-16.png) - 其计算过程图示如下: -![](./img/ch3/3-17.gif) +![](./img/ch3/3.2.3.2.png) 以此类推,计算出全部的Feature Map。 -![](./img/ch3/3-18.png) +![](./img/ch3/3.2.3.4.png) 当步幅为 2 时,Feature Map计算如下 -![](./img/ch3/3-19.png) +![](./img/ch3/3.2.3.5.png) 注:图像大小、步幅和卷积后的Feature Map大小是有关系的。它们满足下面的关系: $$ -W_2 = (W_1 - F + 2P)/S + 1 +W_2 = (W_1 - F + 2P)/S + 1\\ H_2 = (H_1 - F + 2P)/S + 1 $$ -其中 $ W_2 $, 是卷积后 Feature Map 的宽度;$ W_1 $ 是卷积前图像的宽度;$ F $ 是 filter 的宽度;$ P $ 是 Zero Padding 数量,Zero Padding 是指在原始图像周围补几圈 0,如果 P 的值是 1,那么就补 1 圈 0;S 是步幅;$ H_2 $ 卷积后 Feature Map 的高度;$ H_1 $ 是卷积前图像的宽度。 +其中 $ W_2 $, 是卷积后 Feature Map 的宽度;$ W_1 $ 是卷积前图像的宽度;$ F $ 是 filter​ 的宽度;$ P $ 是 Zero Padding 数量,Zero Padding 是指在原始图像周围补几圈 $0$,如果 $P$ 的值是 $1$,那么就补 $1$ 圈 $0$;$S$ 是步幅;$ H_2 $ 卷积后 Feature Map 的高度;$ H_1 $ 是卷积前图像的宽度。 举例:假设图像宽度 $ W_1 = 5 $,filter 宽度 $ F=3 $,Zero Padding $ P=0 $,步幅 $ S=2 $,$ Z $ 则 @@ -275,66 +242,64 @@ $$ 说明 Feature Map 宽度是2。同样,我们也可以计算出 Feature Map 高度也是 2。 -如果卷积前的图像深度为 $ D $,那么相应的 filter 的深度也必须为 $ D $。深度大于 1 的卷积计算公式: +如果卷积前的图像深度为 $ D ​$,那么相应的 filter 的深度也必须为 $ D ​$。深度大于 1 的卷积计算公式: $$ a_{i,j} = f(\sum_{d=0}^{D-1} \sum_{m=0}^{F-1} \sum_{n=0}^{F-1} w_{d,m,n} x_{d,i+m,j+n} + w_b) $$ -其中,$ D $ 是深度;$ F $ 是 filter 的大小;$ w_{d,m,n} $ 表示 filter 的第 $ d $ 层第 $ m $ 行第 $ n $ 列权重;$ a_{d,i,j} $ 表示 feature map 的第 $ d $ 层第 $ i $ 行第 $ j $ 列像素;其它的符号含义前面相同,不再赘述。 +其中,$ D ​$ 是深度;$ F ​$ 是 filter 的大小;$ w_{d,m,n} ​$ 表示 filter 的第 $ d ​$ 层第 $ m ​$ 行第 $ n ​$ 列权重;$ a_{d,i,j} ​$ 表示 feature map 的第 $ d ​$ 层第 $ i ​$ 行第 $ j ​$ 列像素;其它的符号含义前面相同,不再赘述。 -每个卷积层可以有多个 filter。每个 filter 和原始图像进行卷积后,都可以得到一个 Feature Map。卷积后 Feature Map 的深度(个数)和卷积层的 filter 个数是相同的。下面的图示显示了包含两个 filter 的卷积层的计算。7\*7\*3 输入,经过两个 3\*3\*3 filter 的卷积(步幅为 2),得到了 3\*3\*2 的输出。图中的 Zero padding 是 1,也就是在输入元素的周围补了一圈 0。Zero padding 对于图像边缘部分的特征提取是很有帮助的。 +每个卷积层可以有多个 filter。每个 filter 和原始图像进行卷积后,都可以得到一个 Feature Map。卷积后 Feature Map 的深度(个数)和卷积层的 filter 个数相同。下面的图示显示了包含两个 filter 的卷积层的计算。$7*7*3$ 输入,经过两个 $3*3*3$ filter 的卷积(步幅为 $2$),得到了 $3*3*2$ 的输出。图中的 Zero padding 是 $1$,也就是在输入元素的周围补了一圈 $0$。 -![](./img/ch3/3-20.gif) +![](./img/ch3/3.2.3.6.png) -以上就是卷积层的计算方法。这里面体现了局部连接和权值共享:每层神经元只和上一层部分神经元相连(卷积计算规则),且 filter 的权值对于上一层所有神经元都是一样的。对于包含两个 $ 3 * 3 * 3 $ 的 fitler 的卷积层来说,其参数数量仅有 $ (3 * 3 * 3+1) * 2 = 56 $ 个,且参数数量与上一层神经元个数无关。与全连接神经网络相比,其参数数量大大减少了。 +以上就是卷积层的计算方法。这里面体现了局部连接和权值共享:每层神经元只和上一层部分神经元相连(卷积计算规则),且 filter 的权值对于上一层所有神经元都是一样的。对于包含两个 $ 3 * 3 * 3 ​$ 的 fitler 的卷积层来说,其参数数量仅有 $ (3 * 3 * 3+1) * 2 = 56 ​$ 个,且参数数量与上一层神经元个数无关。与全连接神经网络相比,其参数数量大大减少了。 ### 3.2.4 如何计算 Pooling 层输出值输出值? Pooling 层主要的作用是下采样,通过去掉 Feature Map 中不重要的样本,进一步减少参数数量。Pooling 的方法很多,最常用的是 Max Pooling。Max Pooling 实际上就是在 n\*n 的样本中取最大值,作为采样后的样本值。下图是 2\*2 max pooling: -![](./img/ch3/3-21.png) +![](./img/ch3/3.2.4.1.png) -除了 Max Pooing 之外,常用的还有 Mean Pooling ——取各样本的平均值。 -对于深度为 $ D $ 的 Feature Map,各层独立做 Pooling,因此 Pooling 后的深度仍然为 $ D $。 +除了 Max Pooing 之外,常用的还有 Average Pooling ——取各样本的平均值。 +对于深度为 $ D ​$ 的 Feature Map,各层独立做 Pooling,因此 Pooling 后的深度仍然为 $ D ​$。 ### 3.2.5 实例理解反向传播 -答案来源:[一文弄懂神经网络中的反向传播法——BackPropagation](http://www.cnblogs.com/charlotte77/p/5629865.html) - 一个典型的三层神经网络如下所示: -![](./img/ch3/3-22.png) +![](./img/ch3/3.2.5.1.png) -其中 Layer $ L_1 $ 是输入层,Layer $ L_2 $ 是隐含层,Layer $ L_3 $ 是输出层。 +其中 Layer $ L_1 ​$ 是输入层,Layer $ L_2 ​$ 是隐含层,Layer $ L_3 ​$ 是输出层。 假设输入数据集为 $ D={x_1, x_2, ..., x_n} $,输出数据集为 $ y_1, y_2, ..., y_n $。 -如果输入和输出是一样,即为自编码模型。如果原始数据经过映射,会得到不同与输入的输出。 +如果输入和输出是一样,即为自编码模型。如果原始数据经过映射,会得到不同于输入的输出。 假设有如下的网络层: -![](./img/ch3/3-23.png) +![](./img/ch3/3.2.5.2.png) -输入层包含神经元 $ i_1, i_2 $,偏置 $ b_1 $;隐含层包含神经元 $ h_1, h_2 $,偏置 $ b_2 $,输出层为 $ o_1, o_2 $,$ w_i $ 为层与层之间连接的权重,激活函数为 sigmoid 函数。对以上参数取初始值,如下图所示: +输入层包含神经元 $ i_1, i_2 ​$,偏置 $ b_1 ​$;隐含层包含神经元 $ h_1, h_2 ​$,偏置 $ b_2 ​$,输出层为 $ o_1, o_2 ​$,$ w_i ​$ 为层与层之间连接的权重,激活函数为 $sigmoid​$ 函数。对以上参数取初始值,如下图所示: -![](./img/ch3/3-24.png) +![](./img/ch3/3.2.5.3.png) 其中: - 输入数据 $ i1=0.05, i2 = 0.10 $ - 输出数据 $ o1=0.01, o2=0.99 $; - 初始权重 $ w1=0.15, w2=0.20, w3=0.25,w4=0.30, w5=0.40, w6=0.45, w7=0.50, w8=0.55 $ -- 目标:给出输入数据 $ i1,i2 $ (0.05和0.10),使输出尽可能与原始输出 $ o1,o2 $,(0.01和0.99)接近。 +- 目标:给出输入数据 $ i1,i2 $ ( $0.05$和$0.10$ ),使输出尽可能与原始输出 $ o1,o2 $,( $0.01$和$0.99$)接近。 **前向传播** 1. 输入层 --> 输出层 -计算神经元 $ h1 $ 的输入加权和: +计算神经元 $ h1 ​$ 的输入加权和: $$ -net_{h1} = w_1 * i_1 + w_2 * i_2 + b_1 * 1 +net_{h1} = w_1 * i_1 + w_2 * i_2 + b_1 * 1\\ net_{h1} = 0.15 * 0.05 + 0.2 * 0.1 + 0.35 * 1 = 0.3775 $$ @@ -354,23 +319,27 @@ $$ 2. 隐含层-->输出层:    -计算输出层神经元 $ o1 $ 和 $ o2 $ 的值: +计算输出层神经元 $ o1 ​$ 和 $ o2 ​$ 的值: $$ net_{o1} = w_5 * out_{h1} + w_6 * out_{h2} + b_2 * 1 +$$ +$$ net_{o1} = 0.4 * 0.593269992 + 0.45 * 0.596884378 + 0.6 * 1 = 1.105905967 +$$ +$$ out_{o1} = \frac{1}{1 + e^{-net_{o1}}} = \frac{1}{1 + e^{1.105905967}} = 0.75136079 $$ -这样前向传播的过程就结束了,我们得到输出值为 $ [0.75136079 , 0.772928465] $,与实际值 $ [0.01 , 0.99] $ 相差还很远,现在我们对误差进行反向传播,更新权值,重新计算输出。 +这样前向传播的过程就结束了,我们得到输出值为 $ [0.75136079 , 0.772928465] $,与实际值 $ [0.01 , 0.99] ​$ 相差还很远,现在我们对误差进行反向传播,更新权值,重新计算输出。 **反向传播 ** 1. 计算总误差 -总误差:(square error) +总误差:(这里使用$Square$ $Error$) $$ E_{total} = \sum \frac{1}{2}(target - output)^2 @@ -379,16 +348,16 @@ $$ 但是有两个输出,所以分别计算 $ o1 $ 和 $ o2 $ 的误差,总误差为两者之和: $E_{o1} = \frac{1}{2}(target_{o1} - out_{o1})^2 -= \frac{1}{2}(0.01 - 0.75136507)^2 = 0.274811083$ += \frac{1}{2}(0.01 - 0.75136507)^2 = 0.274811083$. -$E_{o2} = 0.023560026$ +$E_{o2} = 0.023560026$. -$E_{total} = E_{o1} + E_{o2} = 0.274811083 + 0.023560026 = 0.298371109$ +$E_{total} = E_{o1} + E_{o2} = 0.274811083 + 0.023560026 = 0.298371109$. 2. 隐含层 --> 输出层的权值更新: -以权重参数 $ w5 $ 为例,如果我们想知道 $ w5 $ 对整体误差产生了多少影响,可以用整体误差对 $ w5 $ 求偏导求出:(链式法则) +以权重参数 $ w5 ​$ 为例,如果我们想知道 $ w5 ​$ 对整体误差产生了多少影响,可以用整体误差对 $ w5 ​$ 求偏导求出:(链式法则) $$ \frac{\partial E_{total}}{\partial w5} = \frac{\partial E_{total}}{\partial out_{o1}} * \frac{\partial out_{o1}}{\partial net_{o1}} * \frac{\partial net_{o1}}{\partial w5} @@ -396,7 +365,7 @@ $$ 下面的图可以更直观的看清楚误差是怎样反向传播的: -![](./img/ch3/3-25.png) +![](./img/ch3/3.2.5.4.png) ### 3.2.6 神经网络更“深”有什么意义? @@ -409,18 +378,23 @@ $$ ### 3.3.1 什么是超参数? -超参数:比如算法中的 learning rate (学习率)、iterations (梯度下降法循环的数量)、(隐藏层数目)、(隐藏层单元数目)、choice of activation function(激活函数的选择)都需要根据实际情况来设置,这些数字实际上控制了最后的参数和的值,所以它们被称作超参数。 +**超参数** : 比如算法中的学习率 ( learning rate )、梯度下降法迭代的数量 ( iterations )、隐藏层数目 ( hidden layers )、隐藏层单元数目、激活函数 ( activation function ) 都需要根据实际情况来设置,这些数字实际上控制了最后的参数和的值,所以它们被称作超参数。 ### 3.3.2 如何寻找超参数的最优值? -在使用机器学习算法时,总有一些难搞的超参数。例如权重衰减大小,高斯核宽度等等。算法不会设置这些参数,而是需要你去设置它们的值。设置的值对结果产生较大影响。常见设置超参数的做法有: +在使用机器学习算法时,总有一些难调的超参数。例如权重衰减大小,高斯核宽度等等。这些参数需要人为设置,设置的值对结果产生较大影响。常见设置超参数的方法有: 1. 猜测和检查:根据经验或直觉,选择参数,一直迭代。 + 2. 网格搜索:让计算机尝试在一定范围内均匀分布的一组值。 + 3. 随机搜索:让计算机随机挑选一组值。 + 4. 贝叶斯优化:使用贝叶斯优化超参数,会遇到贝叶斯优化算法本身就需要很多的参数的困难。 -5. 在良好初始猜测的前提下进行局部优化:这就是 MITIE 的方法,它使用 BOBYQA 算法,并有一个精心选择的起始点。由于 BOBYQA 只寻找最近的局部最优解,所以这个方法是否成功很大程度上取决于是否有一个好的起点。在 MITIE 的情况下,我们知道一个好的起点,但这不是一个普遍的解决方案,因为通常你不会知道好的起点在哪里。从好的方面来说,这种方法非常适合寻找局部最优解。稍后我会再讨论这一点。 -6. 最新提出的 LIPO 的全局优化方法。这个方法没有参数,而且经验证比随机搜索方法好。 + +5. $MITIE$ 方法,好初始猜测的前提下进行局部优化。它使用 $BOBYQA$ 算法,并有一个精心选择的起始点。由于 $BOBYQA$ 只寻找最近的局部最优解,所以这个方法是否成功很大程度上取决于是否有一个好的起点。在 $MITIE​$ 的情况下,我们知道一个好的起点,但这不是一个普遍的解决方案,因为通常你不会知道好的起点在哪里。从好的方面来说,这种方法非常适合寻找局部最优解。稍后我会再讨论这一点。 + +6. 最新提出的 $LIPO​$ 的全局优化方法。这个方法没有参数,而且经验证比随机搜索方法好。 ### 3.3.3 超参数搜索一般过程? @@ -533,7 +507,7 @@ $$ 2. sigmoid 和 tanh 函数的导数在正负饱和区的梯度都会接近于 0,这会造成梯度弥散,而 Relu 和Leaky ReLu 函数大于 0 部分都为常数,不会产生梯度弥散现象。 3. 需注意,Relu 进入负半区的时候,梯度为 0,神经元此时不会训练,产生所谓的稀疏性,而 Leaky ReLu 不会产生这个问题。 -### 3.4.7什么时候可以用线性激活函数? +### 3.4.7 什么时候可以用线性激活函数? 1. 输出层,大多使用线性激活函数。 2. 在隐含层可能会使用一些线性激活函数。 @@ -569,22 +543,24 @@ $$ ​ 从下图看,神经网络中包含了输入层,然后通过两个特征层处理,最后通过 softmax 分析器就能得到不同条件下的概率,这里需要分成三个类别,最终会得到 $ y=0, y=1, y=2 $ 的概率值。 -![](./img/ch3/3-33.png) +![](./img/ch3/3.4.9.1.png) -继续看下面的图,三个输入通过 softmax 后得到一个数组 $ [0.05 , 0.10 , 0.85] $,这就是 soft 的功能。 +继续看下面的图,三个输入通过 softmax 后得到一个数组 $ [0.05 , 0.10 , 0.85] ​$,这就是 soft 的功能。 -![](./img/ch3/3-34.png) +![](./img/ch3/3.4.9.2.png) 更形象的映射过程如下图所示: -![](./img/ch3/3-35.jpg) +![****](./img/ch3/3.4.9.3.png) ​ softmax 直白来说就是将原来输出是 $ 3,1,-3 $ 通过 softmax 函数一作用,就映射成为 $ (0,1) $ 的值,而这些值的累和为 $ 1 $(满足概率的性质),那么我们就可以将它理解成概率,在最后选取输出结点的时候,我们就可以选取概率最大(也就是值对应最大的)结点,作为我们的预测目标! -### 3.4.10 交叉熵代价函数定义及其求导推导。(贡献者:黄钦建-华南理工大学) +### 3.4.10 交叉熵代价函数定义及其求导推导 +(**贡献者:黄钦建-华南理工大学**) -​ 神经元的输出就是 a = σ(z),其中$z=\sum w_{j}i_{j}+b$是输⼊的带权和。 + +​ 神经元的输出就是 a = σ(z),其中$z=\sum w_{j}i_{j}+b​$是输⼊的带权和。 $C=-\frac{1}{n}\sum[ylna+(1-y)ln(1-a)]$ @@ -612,14 +588,16 @@ $\frac{\partial C}{\partial w_{j}}=\frac{1}{n}\sum x_{j}({\varsigma}(z)-y)$ ​ 根据类似的⽅法,我们可以计算出关于偏置的偏导数。我这⾥不再给出详细的过程,你可以轻易验证得到: -$\frac{\partial C}{\partial b}=\frac{1}{n}\sum ({\varsigma}(z)-y)$ +$\frac{\partial C}{\partial b}=\frac{1}{n}\sum ({\varsigma}(z)-y)​$ ​ 再⼀次, 这避免了⼆次代价函数中类似${\varsigma}'(z)$项导致的学习缓慢。 -### 3.4.11 为什么Tanh收敛速度比Sigmoid快?(贡献者:黄钦建-华南理工大学) +### 3.4.11 为什么Tanh收敛速度比Sigmoid快? + +**(贡献者:黄钦建-华南理工大学)** -$tanh^{,}(x)=1-tanh(x)^{2}\in (0,1)$ +$tanh^{,}(x)=1-tanh(x)^{2}\in (0,1)​$ $s^{,}(x)=s(x)*(1-s(x))\in (0,\frac{1}{4}]$ @@ -662,33 +640,35 @@ Batch的选择,首先决定的是下降的方向。 ### 3.5.5 调节 Batch_Size 对训练效果影响到底如何? -1. Batch_Size 太小,模型表现效果极其糟糕(error飙升)。 +1. Batch_Size 太小,模型表现效果极其糟糕(error飙升)。 2. 随着 Batch_Size 增大,处理相同数据量的速度越快。 3. 随着 Batch_Size 增大,达到相同精度所需要的 epoch 数量越来越多。 4. 由于上述两种因素的矛盾, Batch_Size 增大到某个时候,达到时间上的最优。 5. 由于最终收敛精度会陷入不同的局部极值,因此 Batch_Size 增大到某些时候,达到最终收敛精度上的最优。 -### 3.5.6 受限于客观条件无法给足够的Batch Size怎么办? - -在极小的情况下(低于十),建议使用[Group Norm](https://arxiv.org/abs/1803.08494)。 - ## 3.6 归一化 ### 3.6.1 归一化含义? -归一化的具体作用是归纳统一样本的统计分布性。归一化在 $ 0-1$ 之间是统计的概率分布,归一化在$ -1--+1$ 之间是统计的坐标分布。归一化有同一、统一和合一的意思。无论是为了建模还是为了计算,首先基本度量单位要同一,神经网络是以样本在事件中的统计分别几率来进行训练(概率计算)和预测的,且 sigmoid 函数的取值是 0 到 1 之间的,网络最后一个节点的输出也是如此,所以经常要对样本的输出归一化处理。归一化是统一在 $ 0-1 $ 之间的统计概率分布,当所有样本的输入信号都为正值时,与第一隐含层神经元相连的权值只能同时增加或减小,从而导致学习速度很慢。另外在数据中常存在奇异样本数据,奇异样本数据存在所引起的网络训练时间增加,并可能引起网络无法收敛。为了避免出现这种情况及后面数据处理的方便,加快网络学习速度,可以对输入信号进行归一化,使得所有样本的输入信号其均值接近于 0 或与其均方差相比很小。 +1. 归纳统一样本的统计分布性。归一化在 $ 0-1​$ 之间是统计的概率分布,归一化在$ -1--+1​$ 之间是统计的坐标分布。 + +2. 无论是为了建模还是为了计算,首先基本度量单位要同一,神经网络是以样本在事件中的统计分别几率来进行训练(概率计算)和预测,且 sigmoid 函数的取值是 0 到 1 之间的,网络最后一个节点的输出也是如此,所以经常要对样本的输出归一化处理。 + +3. 归一化是统一在 $ 0-1 $ 之间的统计概率分布,当所有样本的输入信号都为正值时,与第一隐含层神经元相连的权值只能同时增加或减小,从而导致学习速度很慢。 + +4. 另外在数据中常存在奇异样本数据,奇异样本数据存在所引起的网络训练时间增加,并可能引起网络无法收敛。为了避免出现这种情况及后面数据处理的方便,加快网络学习速度,可以对输入信号进行归一化,使得所有样本的输入信号其均值接近于 0 或与其均方差相比很小。 ### 3.6.2 为什么要归一化? 1. 为了后面数据处理的方便,归一化的确可以避免一些不必要的数值问题。 -2. 为了程序运行时收敛加快。 下面图解。 +2. 为了程序运行时收敛加快。 3. 同一量纲。样本数据的评价标准不一样,需要对其量纲化,统一评价标准。这算是应用层面的需求。 4. 避免神经元饱和。啥意思?就是当神经元的激活在接近 0 或者 1 时会饱和,在这些区域,梯度几乎为 0,这样,在反向传播过程中,局部梯度就会接近 0,这会有效地“杀死”梯度。 5. 保证输出数据中数值小的不被吞食。 ### 3.6.3 为什么归一化能提高求解最优解速度? -![](./img/ch3/3-36.png) +![](./img/ch3/3.6.3.1.png) 上图是代表数据是否均一化的最优解寻解过程(圆圈可以理解为等高线)。左图表示未经归一化操作的寻解过程,右图表示经过归一化后的寻解过程。 @@ -736,18 +716,16 @@ LRN 是一种提高深度学习准确度的技术方法。LRN 一般是在激活 在 ALexNet 中,提出了 LRN 层,对局部神经元的活动创建竞争机制,使其中响应比较大对值变得相对更大,并抑制其他反馈较小的神经元,增强了模型的泛化能力。 -### 3.6.7理解局部响应归一化公式 +### 3.6.7 理解局部响应归一化 -答案来源:[深度学习的局部响应归一化LRN(Local Response Normalization)理解](https://blog.csdn.net/yangdashi888/article/details/77918311) - -局部响应归一化原理是仿造生物学上活跃的神经元对相邻神经元的抑制现象(侧抑制),根据论文其公式如下: +局部响应归一化原理是仿造生物学上活跃的神经元对相邻神经元的抑制现象(侧抑制),其公式如下: $$ b_{x,y}^i = a_{x,y}^i / (k + \alpha \sum_{j=max(0, i-n/2)}^{min(N-1, i+n/2)}(a_{x,y}^j)^2 )^\beta $$ 其中, -1) $ a $:表示卷积层(包括卷积操作和池化操作)后的输出结果,是一个四维数组[batch,height,width,channel]。 +1) $ a ​$:表示卷积层(包括卷积操作和池化操作)后的输出结果,是一个四维数组[batch,height,width,channel]。 - batch:批次数(每一批为一张图片)。 - height:图片高度。 @@ -760,15 +738,15 @@ $$ 4) $ a $,$ n/2 $, $ k $ 分别表示函数中的 input,depth_radius,bias。参数 $ k, n, \alpha, \beta $ 都是超参数,一般设置 $ k=2, n=5, \alpha=1*e-4, \beta=0.75 $ -5) $ \sum $:$ \sum $ 叠加的方向是沿着通道方向的,即每个点值的平方和是沿着 $ a $ 中的第 3 维 channel 方向的,也就是一个点同方向的前面 $ n/2 $ 个通道(最小为第 $ 0 $ 个通道)和后 $ n/2 $ 个通道(最大为第 $ d-1 $ 个通道)的点的平方和(共 $ n+1 $ 个点)。而函数的英文注解中也说明了把 input 当成是 $ d $ 个 3 维的矩阵,说白了就是把 input 的通道数当作 3 维矩阵的个数,叠加的方向也是在通道方向。 +5) $ \sum ​$:$ \sum ​$ 叠加的方向是沿着通道方向的,即每个点值的平方和是沿着 $ a ​$ 中的第 3 维 channel 方向的,也就是一个点同方向的前面 $ n/2 ​$ 个通道(最小为第 $ 0 ​$ 个通道)和后 $ n/2 ​$ 个通道(最大为第 $ d-1 ​$ 个通道)的点的平方和(共 $ n+1 ​$ 个点)。而函数的英文注解中也说明了把 input 当成是 $ d ​$ 个 3 维的矩阵,说白了就是把 input 的通道数当作 3 维矩阵的个数,叠加的方向也是在通道方向。 简单的示意图如下: -![](./img/ch3/3-38.png) +![](./img/ch3/3.6.7.1.png) ### 3.6.8 什么是批归一化(Batch Normalization) -以前在神经网络训练中,只是对输入层数据进行归一化处理,却没有在中间层进行归一化处理。要知道,虽然我们对输入数据进行了归一化处理,但是输入数据经过 $ \sigma(WX+b) $ 这样的矩阵乘法以及非线性运算之后,其数据分布很可能被改变,而随着深度网络的多层运算之后,数据分布的变化将越来越大。如果我们能在网络的中间也进行归一化处理,是否对网络的训练起到改进作用呢?答案是肯定的。 +以前在神经网络训练中,只是对输入层数据进行归一化处理,却没有在中间层进行归一化处理。要知道,虽然我们对输入数据进行了归一化处理,但是输入数据经过 $ \sigma(WX+b) ​$ 这样的矩阵乘法以及非线性运算之后,其数据分布很可能被改变,而随着深度网络的多层运算之后,数据分布的变化将越来越大。如果我们能在网络的中间也进行归一化处理,是否对网络的训练起到改进作用呢?答案是肯定的。 这种在神经网络中间层也进行归一化处理,使训练效果更好的方法,就是批归一化Batch Normalization(BN)。 @@ -795,7 +773,7 @@ $$ \mu_{\beta} = \frac{1}{m} \sum_{i=1}^m(x_i) $$ -其中,$ m $ 是此次训练样本 batch 的大小。 +其中,$ m ​$ 是此次训练样本 batch 的大小。 2. 计算上一层输出数据的标准差 @@ -821,19 +799,23 @@ $$ 注:上述是 BN 训练时的过程,但是当在投入使用时,往往只是输入一个样本,没有所谓的均值 $ \mu_{\beta} $ 和标准差 $ \sigma_{\beta}^2 $。此时,均值 $ \mu_{\beta} $ 是计算所有 batch $ \mu_{\beta} $ 值的平均值得到,标准差 $ \sigma_{\beta}^2 $ 采用每个batch $ \sigma_{\beta}^2 $ 的无偏估计得到。 -### 3.6.11 批归一化和群组归一化 +### 3.6.11 批归一化和群组归一化比较 -批量归一化(Batch Normalization,以下简称 BN)是深度学习发展中的一项里程碑式技术,可让各种网络并行训练。但是,批量维度进行归一化会带来一些问题——批量统计估算不准确导致批量变小时,BN 的误差会迅速增加。在训练大型网络和将特征转移到计算机视觉任务中(包括检测、分割和视频),内存消耗限制了只能使用小批量的 BN。 +| 名称 | 特点 | +| ------------------------------------------------ | :----------------------------------------------------------- | +| 批量归一化**(Batch Normalization,以下简称 BN) | 可让各种网络并行训练。但是,批量维度进行归一化会带来一些问题——批量统计估算不准确导致批量变小时,BN 的误差会迅速增加。在训练大型网络和将特征转移到计算机视觉任务中(包括检测、分割和视频),内存消耗限制了只能使用小批量的 BN。 | +| 群组归一化** Group Normalization (简称 GN) | GN 将通道分成组,并在每组内计算归一化的均值和方差。GN 的计算与批量大小无关,并且其准确度在各种批量大小下都很稳定。 | +| 比较 | 在 ImageNet 上训练的 ResNet-50上,GN 使用批量大小为 2 时的错误率比 BN 的错误率低 10.6% ;当使用典型的批量时,GN 与 BN 相当,并且优于其他标归一化变体。而且,GN 可以自然地从预训练迁移到微调。在进行 COCO 中的目标检测和分割以及 Kinetics 中的视频分类比赛中,GN 可以胜过其竞争对手,表明 GN 可以在各种任务中有效地取代强大的 BN。 | -何恺明团队在[群组归一化(Group Normalization)](http://tech.ifeng.com/a/20180324/44918599_0.shtml) 中提出群组归一化 Group Normalization (简称 GN) 作为 BN 的替代方案。 +### 3.6.12 Weight Normalization和Batch Normalization比较 -GN 将通道分成组,并在每组内计算归一化的均值和方差。GN 的计算与批量大小无关,并且其准确度在各种批量大小下都很稳定。在 ImageNet 上训练的 ResNet-50上,GN 使用批量大小为 2 时的错误率比 BN 的错误率低 10.6% ;当使用典型的批量时,GN 与 BN 相当,并且优于其他标归一化变体。而且,GN 可以自然地从预训练迁移到微调。在进行 COCO 中的目标检测和分割以及 Kinetics 中的视频分类比赛中,GN 可以胜过其竞争对手,表明 GN 可以在各种任务中有效地取代强大的 BN。 +Weight Normalization 和 Batch Normalization 都属于参数重写(Reparameterization)的方法,只是采用的方式不同。 -### 3.6.12 Weight Normalization和Batch Normalization +Weight Normalization 是对网络权值$ W $ 进行 normalization,因此也称为 Weight Normalization; -答案来源:[Weight Normalization 相比batch Normalization 有什么优点呢?](https://www.zhihu.com/question/55132852/answer/171250929) +Batch Normalization 是对网络某一层输入数据进行 normalization。 -Weight Normalization 和 Batch Normalization 都属于参数重写(Reparameterization)的方法,只是采用的方式不同,Weight Normalization 是对网络权值$ W $ 进行 normalization,因此也称为 Weight Normalization;Batch Normalization 是对网络某一层输入数据进行 normalization。Weight Normalization相比Batch Normalization有以下三点优势: +Weight Normalization相比Batch Normalization有以下三点优势: 1. Weight Normalization 通过重写深度学习网络的权重W的方式来加速深度学习网络参数收敛,没有引入 minbatch 的依赖,适用于 RNN(LSTM)网络(Batch Normalization 不能直接用于RNN,进行 normalization 操作,原因在于:1) RNN 处理的 Sequence 是变长的;2) RNN 是基于 time step 计算,如果直接使用 Batch Normalization 处理,需要保存每个 time step 下,mini btach 的均值和方差,效率低且占内存)。 @@ -841,7 +823,9 @@ Weight Normalization 和 Batch Normalization 都属于参数重写(Reparameter 3. 不需要额外的存储空间来保存 mini batch 的均值和方差,同时实现 Weight Normalization 时,对深度学习网络进行正向信号传播和反向梯度计算带来的额外计算开销也很小。因此,要比采用 Batch Normalization 进行 normalization 操作时,速度快。 但是 Weight Normalization 不具备 Batch Normalization 把网络每一层的输出 Y 固定在一个变化范围的作用。因此,采用 Weight Normalization 进行 Normalization 时需要特别注意参数初始值的选择。 -### 3.6.13 Batch Normalization在什么时候用比较合适?(贡献者:黄钦建-华南理工大学) +### 3.6.13 Batch Normalization在什么时候用比较合适? + +**(贡献者:黄钦建-华南理工大学)** 在CNN中,BN应作用在非线性映射前。在神经网络训练时遇到收敛速度很慢,或梯度爆炸等无法训练的状况时可以尝试BN来解决。另外,在一般使用情况下也可以加入BN来加快训练速度,提高模型精度。 @@ -851,8 +835,6 @@ BN比较适用的场景是:每个mini-batch比较大,数据分布比较接 ## 3.7 预训练与微调(fine tuning) ### 3.7.1 为什么无监督预训练可以帮助深度学习? -答案来源:[为什么无监督的预训练可以帮助深度学习](http://blog.csdn.net/Richard_More/article/details/52334272?locationNum=3&fps=1) - 深度网络存在问题: 1. 网络越深,需要的训练样本数越多。若用监督则需大量标注样本,不然小规模样本容易造成过拟合。深层网络特征比较多,会出现的多特征问题主要有多样本问题、规则化问题、特征选择问题。 @@ -877,7 +859,7 @@ BN比较适用的场景是:每个mini-batch比较大,数据分布比较接 ### 3.7.3 微调时候网络参数是否更新? -会更新。 +答案:会更新。 1. finetune 的过程相当于继续训练,跟直接训练的区别是初始化的时候。 2. 直接训练是按照网络定义指定的方式初始化。 @@ -910,20 +892,30 @@ BN比较适用的场景是:每个mini-batch比较大,数据分布比较接 以一个三层网络为例: 首先看下结构 -![](./img/ch3/3-39.jpg) +![](./img/ch3/3.8.2.1.png) 它的表达式为: $$ a_1^{(2)} = f(W_{11}^{(1)} x_1 + W_{12}^{(1)} x_2 + W_{13}^{(1)} x_3 + b_1^{(1)}) +$$ +$$ a_2^{(2)} = f(W_{21}^{(1)} x_1 + W_{22}^{(1)} x_2 + W_{23}^{(1)} x_3 + b_2^{(1)}) +$$ +$$ a_3^{(2)} = f(W_{31}^{(1)} x_1 + W_{32}^{(1)} x_2 + W_{33}^{(1)} x_3 + b_3^{(1)}) +$$ +$$ h_{W,b}(x) = a_1^{(3)} = f(W_{11}^{(2)} a_1^{(2)} + W_{12}^{(2)} a_2^{(2)} + W_{13}^{(2)} a_3^{(2)} + b_1^{(2)}) $$ +$$ +xa_1^{(2)} = f(W_{11}^{(1)} x_1 + W_{12}^{(1)} x_2 + W_{13}^{(1)} x_3 + b_1^{(1)})a_2^{(2)} = f(W_{21}^{(1)} x_1 + W_{22}^{(1)} x_2 + W_{23}^{(1)} x_3 + +$$ + 如果每个权重都一样,那么在多层网络中,从第二层开始,每一层的输入值都是相同的了也就是$ a1=a2=a3=.... $,既然都一样,就相当于一个输入了,为啥呢?? 如果是反向传递算法(如果这里不明白请看上面的连接),其中的偏置项和权重项的迭代的偏导数计算公式如下 @@ -934,7 +926,7 @@ $$ \frac{\partial}{\partial b_{i}^{(l)}} J(W,b;x,y) = \delta_i^{(l+1)} $$ -$ \delta $ 的计算公式 +$ \delta ​$ 的计算公式 $$ \delta_i^{(l)} = (\sum_{j=1}^{s_{t+1}} W_{ji}^{(l)} \delta_j^{(l+1)} ) f^{\prime}(z_i^{(l)}) @@ -951,7 +943,7 @@ $$ ### 3.8.3 初始化为小的随机数 -将权重初始化为很小的数字是一个普遍的打破网络对称性的解决办法。这个想法是,神经元在一开始都是随机的、独一无二的,所以它们会计算出不同的更新,并将自己整合到整个网络的各个部分。一个权重矩阵的实现可能看起来像 $ W=0.01∗np.random.randn(D,H) $,其中 randn 是从均值为 0 的单位标准高斯分布进行取样。通过这个公式(函数),每个神经元的权重向量初始化为一个从多维高斯分布取样的随机向量,所以神经元在输入空间中指向随机的方向(so the neurons point in random direction in the input space). 应该是指输入空间对于随机方向有影响)。其实也可以从均匀分布中来随机选取小数,但是在实际操作中看起来似乎对最后的表现并没有太大的影响。 +将权重初始化为很小的数字是一个普遍的打破网络对称性的解决办法。这个想法是,神经元在一开始都是随机的、独一无二的,所以它们会计算出不同的更新,并将自己整合到整个网络的各个部分。一个权重矩阵的实现可能看起来像 $ W=0.01∗np.random.randn(D,H) ​$,其中 randn 是从均值为 0 的单位标准高斯分布进行取样。通过这个公式(函数),每个神经元的权重向量初始化为一个从多维高斯分布取样的随机向量,所以神经元在输入空间中指向随机的方向(so the neurons point in random direction in the input space). 应该是指输入空间对于随机方向有影响)。其实也可以从均匀分布中来随机选取小数,但是在实际操作中看起来似乎对最后的表现并没有太大的影响。 备注:警告:并不是数字越小就会表现的越好。比如,如果一个神经网络层的权重非常小,那么在反向传播算法就会计算出很小的梯度(因为梯度 gradient 是与权重成正比的)。在网络不断的反向传播过程中将极大地减少“梯度信号”,并可能成为深层网络的一个需要注意的问题。 @@ -1059,8 +1051,8 @@ tf.train.RMSPropOptimizer ### 3.12.2 为什么正则化有利于预防过拟合? -![](./img/ch3/3-40.png) -![](./img/ch3/3-41.png) +![](./img/ch3/3.12.2.1.png) +![](./img/ch3/3.12.2.2.png) 左图是高偏差,右图是高方差,中间是Just Right,这几张图我们在前面课程中看到过。 @@ -1082,8 +1074,9 @@ Dropout可以随机删除网络中的神经单元,它为什么可以通过正 dropout一大缺点就是代价函数J不再被明确定义,每次迭代,都会随机移除一些节点,如果再三检查梯度下降的性能,实际上是很难进行复查的。定义明确的代价函数J每次迭代后都会下降,因为我们所优化的代价函数J实际上并没有明确定义,或者说在某种程度上很难计算,所以我们失去了调试工具来绘制这样的图片。我通常会关闭dropout函数,将keep-prob的值设为1,运行代码,确保J函数单调递减。然后打开dropout函数,希望在dropout过程中,代码并未引入bug。我觉得你也可以尝试其它方法,虽然我们并没有关于这些方法性能的数据统计,但你可以把它们与dropout方法一起使用。 +## 3.13 深度学习中常用的数据增强方法(Data Augmentation)? -## 3.13 深度学习中常用的数据增强方法(Data Augmentation)?(贡献者:黄钦建-华南理工大学) +**(贡献者:黄钦建-华南理工大学)** - Color Jittering:对颜色的数据增强:图像亮度、饱和度、对比度变化(此处对色彩抖动的理解不知是否得当); @@ -1103,7 +1096,9 @@ dropout一大缺点就是代价函数J不再被明确定义,每次迭代,都 - Label Shuffle:类别不平衡数据的增广; -## 3.14 如何理解 Internal Covariate Shift?(贡献者:黄钦建-华南理工大学) +## 3.14 如何理解 Internal Covariate Shift? + +**(贡献者:黄钦建-华南理工大学)** 深度神经网络模型的训练为什么会很困难?其中一个重要的原因是,深度神经网络涉及到很多层的叠加,而每一层的参数更新会导致上层的输入数据分布发生变化,通过层层叠加,高层的输入分布变化会非常剧烈,这就使得高层需要不断去重新适应底层的参数更新。为了训好模型,我们需要非常谨慎地去设定学习率、初始化权重、以及尽可能细致的参数更新策略。 @@ -1123,7 +1118,9 @@ Google 将这一现象总结为 Internal Covariate Shift,简称 ICS。 什么 其三,每层的更新都会影响到其它层,因此每层的参数更新策略需要尽可能的谨慎。 -## 3.15 什么时候用local-conv?什么时候用全卷积?(贡献者:梁志成-魅族科技) +## 3.15 什么时候用local-conv?什么时候用全卷积? + +**(贡献者:梁志成-魅族科技)** 1.当数据集具有全局的局部特征分布时,也就是说局部特征之间有较强的相关性,适合用全卷积。 diff --git "a/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/\347\254\254\344\270\211\347\253\240_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200.pdf" "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/\347\254\254\344\270\211\347\253\240_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200.pdf" new file mode 100644 index 00000000..4a6b7849 Binary files /dev/null and "b/ch03_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200/\347\254\254\344\270\211\347\253\240_\346\267\261\345\272\246\345\255\246\344\271\240\345\237\272\347\241\200.pdf" differ diff --git "a/ch06_\345\276\252\347\216\257\347\245\236\347\273\217\347\275\221\347\273\234(RNN)/\347\254\254\345\205\255\347\253\240_\345\276\252\347\216\257\347\245\236\347\273\217\347\275\221\347\273\234(RNN).md" "b/ch06_\345\276\252\347\216\257\347\245\236\347\273\217\347\275\221\347\273\234(RNN)/\347\254\254\345\205\255\347\253\240_\345\276\252\347\216\257\347\245\236\347\273\217\347\275\221\347\273\234(RNN).md" index aef232d6..224d3d29 100644 --- "a/ch06_\345\276\252\347\216\257\347\245\236\347\273\217\347\275\221\347\273\234(RNN)/\347\254\254\345\205\255\347\253\240_\345\276\252\347\216\257\347\245\236\347\273\217\347\275\221\347\273\234(RNN).md" +++ "b/ch06_\345\276\252\347\216\257\347\245\236\347\273\217\347\275\221\347\273\234(RNN)/\347\254\254\345\205\255\347\253\240_\345\276\252\347\216\257\347\245\236\347\273\217\347\275\221\347\273\234(RNN).md" @@ -26,8 +26,7 @@ LSTM 的核心思想? 如何逐步理解LSTM? 常见的RNNs扩展和改进模型 RNN种类? -讲解CNN+RNN的各种组合方式 http://www.elecfans.com/d/775895.html -RNN学习和实践过程中常常碰到的疑问 +讲解CNN+RNN的各种组合方式 http://www.elecfans.com/d/775895.html ## CNN和RNN的对比 http://www.elecfans.com/d/775895.html 1、CNN卷积神经网络与RNN递归神经网络直观图 2、相同点: @@ -37,8 +36,7 @@ RNN学习和实践过程中常常碰到的疑问 3、不同点 3.1. CNN空间扩展,神经元与特征卷积;RNN时间扩展,神经元与多个时间输出计算 3.2. RNN可以用于描述时间上连续状态的输出,有记忆功能,CNN用于静态输出 -3.3. CNN高级100+深度,RNN深度有限 - +3. 3. CNN高级100+深度,RNN深度有限 http://blog.csdn.net/heyongluoyao8/article/details/48636251 @@ -247,9 +245,3 @@ CW-RNNs与SRNs网络结构类似,也包括输入层(Input)、隐藏层(Hidden) ### 6.6.10 CNN-LSTMs 1. 为了同时利用CNN以及LSTMs的优点,CNN-LSTMs被提出。在该模型中,CNN用于提取对象特征,LSTMs用于预测。CNN由于卷积特性,其能够快速而且准确地捕捉对象特征。LSTMs的优点在于能够捕捉数据间的长时依赖性。 - - - -### 6.7 常见疑问 -1. 从学习RNN伊始,常常说RNN结构可以解决不定长的数据,不像CNN中一般输入数据是图片,是一般是在建网络结构开始把图片resize到固定宽高,而RNN能解决不定长,这里指的是,time_steps可以不固定,而每次time,input的维度这是固定的。比如,语音特征数据或时间序列数据,一个完整的数据,时间帧数上可以不固定,但每帧的数据维度是固定的。 -2. time_steps的不固定,在构建计算图中,就相当于是构建是动态神经网络图,因为每个数据的时间维度是不固定的,这在编程过程中,Tensorflow其实是以静态图著称,但TensorFlow中提供了**tf.nn.dynamic_rnn()**,达到动态图机制,,但是还是建议大家用PyTorch去搭建RNN模型,因为Pytorch原生就是动态图著称,理解上更容易。 \ No newline at end of file diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/._ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/._ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)" new file mode 100644 index 00000000..32ff51d9 Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/._ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/._.DS_Store" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/._.DS_Store" new file mode 100644 index 00000000..09fa6bdd Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/._.DS_Store" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/._ch7.md" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/._ch7.md" new file mode 100644 index 00000000..23692b1b Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/._ch7.md" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/._ch7.pdf" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/._ch7.pdf" new file mode 100644 index 00000000..156ee3fc Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/._ch7.pdf" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/._img" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/._img" new file mode 100644 index 00000000..32ff51d9 Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/._img" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/._.DS_Store" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/._.DS_Store" new file mode 100644 index 00000000..09fa6bdd Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/._.DS_Store" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/._ch7" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/._ch7" new file mode 100644 index 00000000..32ff51d9 Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/._ch7" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._.DS_Store" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._.DS_Store" new file mode 100644 index 00000000..09fa6bdd Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._.DS_Store" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._7.1-gan_structure.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._7.1-gan_structure.png" new file mode 100644 index 00000000..32ff51d9 Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._7.1-gan_structure.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._Boundary_map.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._Boundary_map.png" new file mode 100644 index 00000000..32ff51d9 Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._Boundary_map.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._CGAN\347\275\221\347\273\234\347\273\223\346\236\204.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._CGAN\347\275\221\347\273\234\347\273\223\346\236\204.png" new file mode 100644 index 00000000..32ff51d9 Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._CGAN\347\275\221\347\273\234\347\273\223\346\236\204.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._CycleGAN\346\250\241\345\236\213\347\244\272\346\204\217\345\233\276.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._CycleGAN\346\250\241\345\236\213\347\244\272\346\204\217\345\233\276.png" new file mode 100644 index 00000000..99e89880 Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._CycleGAN\346\250\241\345\236\213\347\244\272\346\204\217\345\233\276.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._CycleGAN\347\273\223\346\236\234\344\276\213\345\255\220.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._CycleGAN\347\273\223\346\236\234\344\276\213\345\255\220.png" new file mode 100644 index 00000000..dd7f9f35 Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._CycleGAN\347\273\223\346\236\234\344\276\213\345\255\220.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._DCGAN\347\273\223\346\236\204\345\233\276.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._DCGAN\347\273\223\346\236\204\345\233\276.png" new file mode 100644 index 00000000..fc2b9af3 Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._DCGAN\347\273\223\346\236\204\345\233\276.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._DCGAN\350\276\223\345\205\245\345\231\252\345\243\260\347\220\206\350\247\243.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._DCGAN\350\276\223\345\205\245\345\231\252\345\243\260\347\220\206\350\247\243.png" new file mode 100644 index 00000000..52386ff7 Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._DCGAN\350\276\223\345\205\245\345\231\252\345\243\260\347\220\206\350\247\243.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._DCGAN\350\276\223\345\205\245\345\231\252\345\243\260\347\256\227\346\234\257\350\277\220\347\256\227.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._DCGAN\350\276\223\345\205\245\345\231\252\345\243\260\347\256\227\346\234\257\350\277\220\347\256\227.png" new file mode 100644 index 00000000..5cb9c2a4 Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._DCGAN\350\276\223\345\205\245\345\231\252\345\243\260\347\256\227\346\234\257\350\277\220\347\256\227.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._LSGAN\344\272\244\345\217\211\347\206\265\344\270\216\346\234\200\345\260\217\344\272\214\344\271\230\346\215\237\345\244\261\345\257\271\346\257\224\345\233\276.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._LSGAN\344\272\244\345\217\211\347\206\265\344\270\216\346\234\200\345\260\217\344\272\214\344\271\230\346\215\237\345\244\261\345\257\271\346\257\224\345\233\276.png" new file mode 100644 index 00000000..09ec3055 Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._LSGAN\344\272\244\345\217\211\347\206\265\344\270\216\346\234\200\345\260\217\344\272\214\344\271\230\346\215\237\345\244\261\345\257\271\346\257\224\345\233\276.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._Wass\350\267\235\347\246\273\351\232\217\350\277\255\344\273\243\346\254\241\346\225\260\345\217\230\345\214\226.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._Wass\350\267\235\347\246\273\351\232\217\350\277\255\344\273\243\346\254\241\346\225\260\345\217\230\345\214\226.png" new file mode 100644 index 00000000..d289d139 Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._Wass\350\267\235\347\246\273\351\232\217\350\277\255\344\273\243\346\254\241\346\225\260\345\217\230\345\214\226.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._cycleGAN\346\225\260\346\215\256\345\242\236\345\271\277.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._cycleGAN\346\225\260\346\215\256\345\242\236\345\271\277.png" new file mode 100644 index 00000000..3b96df81 Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._cycleGAN\346\225\260\346\215\256\345\242\236\345\271\277.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._mode_dropping.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._mode_dropping.png" new file mode 100644 index 00000000..c2e56543 Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._mode_dropping.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._model_collpsing.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._model_collpsing.png" new file mode 100644 index 00000000..ebfe9a89 Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._model_collpsing.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._pix2pixHD_Loss.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._pix2pixHD_Loss.png" new file mode 100644 index 00000000..32ff51d9 Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._pix2pixHD_Loss.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._pix2pixHD\347\275\221\347\273\234\347\273\223\346\236\204.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._pix2pixHD\347\275\221\347\273\234\347\273\223\346\236\204.png" new file mode 100644 index 00000000..32ff51d9 Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._pix2pixHD\347\275\221\347\273\234\347\273\223\346\236\204.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._pix2pix_Loss.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._pix2pix_Loss.png" new file mode 100644 index 00000000..32ff51d9 Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._pix2pix_Loss.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._pix2pix\346\250\241\345\236\213\347\244\272\346\204\217\345\233\276.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._pix2pix\346\250\241\345\236\213\347\244\272\346\204\217\345\233\276.png" new file mode 100644 index 00000000..32ff51d9 Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._pix2pix\346\250\241\345\236\213\347\244\272\346\204\217\345\233\276.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._pix2pix\347\273\223\346\236\234\347\244\272\344\276\213.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._pix2pix\347\273\223\346\236\234\347\244\272\344\276\213.png" new file mode 100644 index 00000000..32ff51d9 Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._pix2pix\347\273\223\346\236\234\347\244\272\344\276\213.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._pix2pix\350\257\255\344\271\211\345\234\260\345\233\276L1loss\347\273\223\346\236\234.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._pix2pix\350\257\255\344\271\211\345\234\260\345\233\276L1loss\347\273\223\346\236\234.png" new file mode 100644 index 00000000..32ff51d9 Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._pix2pix\350\257\255\344\271\211\345\234\260\345\233\276L1loss\347\273\223\346\236\234.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._readme.md" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._readme.md" new file mode 100644 index 00000000..32ff51d9 Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._readme.md" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._seqGAN\346\250\241\345\236\213.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._seqGAN\346\250\241\345\236\213.png" new file mode 100644 index 00000000..4de1248d Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._seqGAN\346\250\241\345\236\213.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._starGAN\345\212\240\345\205\245mask\347\244\272\346\204\217\345\233\276.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._starGAN\345\212\240\345\205\245mask\347\244\272\346\204\217\345\233\276.png" new file mode 100644 index 00000000..dd2d52c0 Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._starGAN\345\212\240\345\205\245mask\347\244\272\346\204\217\345\233\276.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._starGAN\346\250\241\345\236\213\347\273\223\346\236\204.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._starGAN\346\250\241\345\236\213\347\273\223\346\236\204.png" new file mode 100644 index 00000000..cc8b39cf Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._starGAN\346\250\241\345\236\213\347\273\223\346\236\204.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._upsample.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._upsample.png" new file mode 100644 index 00000000..32ff51d9 Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._upsample.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._\350\257\255\344\271\211\347\274\226\350\276\221.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._\350\257\255\344\271\211\347\274\226\350\276\221.png" new file mode 100644 index 00000000..32ff51d9 Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/__MACOSX/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/._\350\257\255\344\271\211\347\274\226\350\276\221.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch7.md" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch7.md" new file mode 100644 index 00000000..334adfee --- /dev/null +++ "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch7.md" @@ -0,0 +1,454 @@ +[TOC] + + + +# Author + +@中科院-郭晓锋 + +# TODO + +- [x] 加入整章的框架图 +- [x] 加入GAN在语音,文字当中的应用:文本到图像的翻译,文本生成(SeqGAN) +- [x] GAN为什么在文本,语音处理任务上效果不佳? +- [x] 整理继勇给的github上面的资料 +- [x] 补充GAN在语音领域,数据增广,超分辨与图像复原当中的应用 +- [x] 生成模型的评价标准 +- [x] 补充GAN评价指标对比,以及评价指标本身的优缺点。 +- [x] 多读GAN的综述,提升Insight +- [ ] 合理组织语言,保证逻辑严谨,思路清晰 + +# 7 生成对抗网络 + +## 7.1 GAN基本概念 +### 7.1.1 什么是生成对抗网络? +#### 如何通俗理解GAN? + +生成对抗网络(GAN, Generative adversarial network)自从2014年被Ian Goodfellow提出以来,掀起来了一股研究热潮。GAN由生成器和判别器组成,生成器负责生成样本,判别器负责判断生成器生成的样本是否为真。生成器要尽可能迷惑判别器,而判别器要尽可能区分生成器生成的样本和真实样本。 + +在GAN的原作[1]中,作者将生成器比喻为印假钞票的犯罪分子,判别器则类比为警察。犯罪分子努力让钞票看起来逼真,警察则不断提升对于假钞的辨识能力。二者互相博弈,随着时间的进行,都会越来越强。那么类比于图像生成任务,生成器不断生成尽可能逼真的假图像。判别器则判断图像是否是真实的图像,还是生成的图像,二者不断博弈优化。最终生成器生成的图像使得判别器完全无法判别真假。 + +#### GAN的形式化表达 +上述例子只是简要介绍了一下GAN的思想,下面对于GAN做一个形式化的,更加具体的定义。通常情况下,无论是生成器还是判别器,我们都可以用神经网络来实现。那么,我们可以把通俗化的定义用下面这个模型来表示: +![GAN网络结构](./img/ch7/7.1-gan_structure.png) + +上述模型左边是生成器G,其输入是$z$,对于原始的GAN,$z$是由高斯分布随机采样得到的噪声。噪声$z$通过生成器得到了生成的假样本。 + +生成的假样本与真实样本放到一起,被随机抽取送入到判别器D,由判别器去区分输入的样本是生成的假样本还是真实的样本。整个过程简单明了,生成对抗网络中的“生成对抗”主要体现在生成器和判别器之间的对抗。 + +#### GAN的目标函数是什么? +对于上述神经网络模型,如果想要学习其参数,首先需要一个目标函数。GAN的目标函数定义如下: + +$$ +\mathop {\min }\limits_G \mathop {\max }\limits_D V(D,G) = {{\rm E}_{x\sim{p_{data}}(x)}}[\log D(x)] + {{\rm E}_{z\sim{p_z}(z)}}[\log (1 - D(G(z)))] +$$ +这个目标函数可以分为两个部分来理解: + +判别器的优化通过$\mathop {\max}\limits_D V(D,G)​$实现,$V(D,G)​$为判别器的目标函数,其第一项${{\rm E}_{x\sim{p_{data}}(x)}}[\log D(x)]​$表示对于从真实数据分布 中采用的样本 ,其被判别器判定为真实样本概率的数学期望。对于真实数据分布 中采样的样本,其预测为正样本的概率当然是越接近1越好。因此希望最大化这一项。第二项${{\rm E}_{z\sim{p_z}(z)}}[\log (1 - D(G(z)))]​$表示:对于从噪声P_z(z)分布当中采样得到的样本经过生成器生成之后得到的生成图片,然后送入判别器,其预测概率的负对数的期望,这个值自然是越大越好,这个值越大, 越接近0,也就代表判别器越好。 + +生成器的优化通过$\mathop {\min }\limits_G({\mathop {\max }\limits_D V(D,G)})​$实现。注意,生成器的目标不是$\mathop {\min }\limits_GV(D,G)​$,即生成器**不是最小化判别器的目标函数**,生成器最小化的是**判别器目标函数的最大值**,判别器目标函数的最大值代表的是真实数据分布与生成数据分布的JS散度(详情可以参阅附录的推导),JS散度可以度量分布的相似性,两个分布越接近,JS散度越小。 + + +#### GAN的目标函数和交叉熵有什么区别? +判别器目标函数写成离散形式即为: +$$ +V(D,G)=-\frac{1}{m}\sum_{i=1}^{i=m}logD(x^i)-\frac{1}{m}\sum_{i=1}^{i=m}log(1-D(\tilde{x}^i)) +$$ + +可以看出,这个目标函数和交叉熵是一致的,即**判别器的目标是最小化交叉熵损失,生成器的目标是最小化生成数据分布和真实数据分布的JS散度** + +------------------- +[1]: Goodfellow, Ian, et al. "Generative adversarial nets." Advances in neural information processing systems. 2014. + +### 7.1.2 GAN的Loss为什么降不下去? + +对于很多GAN的初学者在实践过程中可能会纳闷,为什么GAN的Loss一直降不下去。GAN到底什么时候才算收敛?其实,作为一个训练良好的GAN,其Loss就是降不下去的。衡量GAN是否训练好了,只能由人肉眼去看生成的图片质量是否好。不过,对于没有一个很好的评价是否收敛指标的问,也有许多学者做了一些研究,后文提及的WGAN就提出了一种新的Loss设计方式,较好的解决了难以判断收敛性的问题。下面我们分析一下GAN的Loss为什么降不下去? +对于判别器而言,GAN的Loss如下: +$$\mathop {\min }\limits_G \mathop {\max }\limits_D V(D,G) = {{\rm E}_{x\sim{p_{data}}(x)}}[\log D(x)] + {{\rm E}_{z\sim{p_z}(z)}}[\log (1 - D(G(z)))]$$ +从$\mathop {\min }\limits_G \mathop {\max }\limits_D V(D,G)​$可以看出,生成器和判别器的目的相反,也就是说两个生成器网络和判别器网络互为对抗,此消彼长。不可能Loss一直降到一个收敛的状态。 + +- 对于生成器,其Loss下降快,很有可能是判别器太弱,导致生成器很轻易的就"愚弄"了判别器。 +- 对于判别器,其Loss下降快,意味着判别器很强,判别器很强则说明生成器生成的图像不够逼真,才使得判别器轻易判别,导致Loss下降很快。 + +也就是说,无论是判别器,还是生成器。loss的高低不能代表生成器的好坏。一个好的GAN网络,其GAN Loss往往是不断波动的。 +看到这里可能有点让人绝望,似乎判断模型是否收敛就只能看生成的图像质量了。实际上,后文探讨的WGAN,提出了一种新的loss度量方式,让我们可以通过一定的手段来判断模型是否收敛 + +### 7.1.3 生成式模型、判别式模型的区别? + +对于机器学习模型,我们可以根据模型对数据的建模方式将模型分为两大类,生成式模型和判别式模型。如果我们要训练一个关于猫狗分类的模型,对于判别式模型,只需要学习二者差异即可。比如说猫的体型会比狗小一点。而生成式模型则不一样,需要学习猫张什么样,狗张什么样。有了二者的长相以后,再根据长相去区分。具体而言: + +- 生成式模型:由数据学习联合概率分布P(X,Y), 然后由P(Y|X)=P(X,Y)/P(X)求出概率分布P(Y|X)作为预测的模型。该方法表示了给定输入X与产生输出Y的生成关系 + +- 判别式模型:由数据直接学习决策函数Y=f(X)或条件概率分布P(Y|X)作为预测模型,即判别模型。判别方法关心的是对于给定的输入X,应该预测什么样的输出Y。 + +对于上述两种模型,从文字上理解起来似乎不太直观。我们举个例子来阐述一下,对于性别分类问题,分别用不同的模型来做: + +1)如果用生成式模型:可以训练一个模型,学习输入人的特征X和性别Y的关系。比如现在有下面一批数据: + +Y | 0 1 + +X | 0 1/4 3/4 + + | 1 3/4 1/4 + +这个数据可以统计得到,即统计人的特征X=0,1….的时候,其类别为Y=0,1的概率。统计得到上述联合概率分布P(X, Y)后,可以学习一个模型,比如让二维高斯分布去拟合上述数据,这样就学习到了X,Y的联合分布。在预测时,如果我们希望给一个输入特征X,预测其类别,则需要通过贝叶斯公式得到条件概率分布才能进行推断: + +​ $$P(Y|X)={\frac{P(X,Y)}{P(X)}}={\frac{P(X,Y)}{P(X|Y)P(Y)}}$$ + +2)如果用判别式模型:可以训练一个模型,输入人的特征X,这些特征包括人的五官,穿衣风格,发型等。输出则是对于性别的判断概率,这个概率服从一个分布,分布的取值只有两个,要么男,要么女,记这个分布为Y。这个过程学习了一个条件概率分布P(Y|X),即输入特征X的分布已知条件下,Y的概率分布。 + +显然,从上面的分析可以看出。判别式模型似乎要方便很多,因为生成式模型要学习一个X,Y的联合分布往往需要很多数据,而判别式模型需要的数据则相对少,因为判别式模型更关注输入特征的差异性。不过生成式既然使用了更多数据来生成联合分布,自然也能够提供更多的信息,现在有一个样本(X,Y),其联合概率P(X,Y)经过计算特别小,那么可以认为这个样本是异常样本。这种模型可以用来做outlier detection。 + +### 7.1.4 什么是mode collapsing? + +#### 什么是mode collapsing? + +某个模式(mode)出现大量重复样本,例如: +![model collapsing](./img/ch7/model_collpsing.png) +上图左侧的蓝色五角星表示真实样本空间,黄色的是生成的。生成样本缺乏多样性,存在大量重复。比如上图右侧中,红框里面人物反复出现。 + +#### 如何解决mode collapsing? + +**针对目标函数的改进方法** + +为了避免前面提到的由于优化maxmin导致mode跳来跳去的问题,UnrolledGAN采用修改生成器loss来解决。具体而言,UnrolledGAN在更新生成器时更新k次生成器,参考的Loss不是某一次的loss,是判别器后面k次迭代的loss。注意,判别器后面k次迭代不更新自己的参数,只计算loss用于更新生成器。这种方式使得生成器考虑到了后面k次判别器的变化情况,避免在不同mode之间切换导致的模式崩溃问题。此处务必和迭代k次生成器,然后迭代1次判别器区分开[8]。DRAGAN则引入博弈论中的无后悔算法,改造其loss以解决mode collapse问题[9]。前文所述的EBGAN则是加入VAE的重构误差以解决mode collapse。 + +**针对网络结构的改进方法** + +Multi agent diverse GAN(MAD-GAN)采用多个生成器,一个判别器以保障样本生成的多样性。具体结构如下: + +![](/Users/xfguo/Desktop/blog/zhihu/imgs/MAD_GAN.png) + +相比于普通GAN,多了几个生成器,且在loss设计的时候,加入一个正则项。正则项使用余弦距离惩罚三个生成器生成样本的一致性。 + +MRGAN则添加了一个判别器来惩罚生成样本的mode collapse问题。具体结构如下: + +![](/Users/xfguo/Desktop/blog/zhihu/imgs/MRGAN.png) + +输入样本$x$通过一个Encoder编码为隐变量$E(x)$,然后隐变量被Generator重构,训练时,Loss有三个。$D_M$和$R$(重构误差)用于指导生成real-like的样本。而$D_D$则对$E(x)$和$z$生成的样本进行判别,显然二者生成样本都是fake samples,所以这个判别器主要用于判断生成的样本是否具有多样性,即是否出现mode collapse。 + +**Mini-batch Discrimination** + +Mini-batch discrimination在判别器的中间层建立一个mini-batch layer用于计算基于L1距离的样本统计量,通过建立该统计量,实现了一个batch内某个样本与其他样本有多接近。这个信息可以被判别器利用到,从而甄别出哪些缺乏多样性的样本。对生成器而言,则要试图生成具有多样性的样本。 + +### 7.1.5 如何客观评价GAN的生成能力? + +最常见评价GAN的方法就是主观评价。主观评价需要花费大量人力物力,且存在以下问题: + +- 评价带有主管色彩,有些bad case没看到很容易造成误判 + +- 如果一个GAN过拟合了,那么生成的样本会非常真实,人类主观评价得分会非常高,可是这并不是一个好的GAN。 + +因此,就有许多学者提出了GAN的客观评价方法。 + +#### Inception Score + +对于一个在ImageNet训练良好的GAN,其生成的样本丢给Inception网络进行测试的时候,得到的判别概率应该具有如下特性: +- 对于同一个类别的图片,其输出的概率分布应该趋向于一个脉冲分布。可以保证生成样本的准确性。 +- 对于所有类别,其输出的概率分布应该趋向于一个均匀分布,这样才不会出现mode dropping等,可以保证生成样本的多样性。 + +因此,可以设计如下指标: +$$IS(P_g)=e^{E_{x\sim P_g}[KL(p_M(y|x)\Vert{p_M(y)})]}$$ +根据前面分析,如果是一个训练良好的GAN,$p_M(y|x)$趋近于脉冲分布,$p_M(y)$趋近于均匀分布。二者KL散度会很大。Inception Score自然就高。实际实验表明,Inception Score和人的主观判别趋向一致。IS的计算没有用到真实数据,具体值取决于模型M的选择 + +**特点:可以一定程度上衡量生成样本的多样性和准确性,但是无法检测过拟合。Mode Score也是如此。不推荐在和ImageNet数据集差别比较大的数据上使用。** + +#### Mode Score + +Mode Score作为Inception Score的改进版本,添加了关于生成样本和真实样本预测的概率分布相似性度量一项。具体公式如下: +$$MS(P_g)=e^{E_{x\sim P_g}[KL(p_M(y|x)\Vert{p_M(y)})-KL(p_M(y)\Vert p_M(y^*))]}$$ + +#### Kernel MMD (Maximum Mean Discrepancy) + +计算公式如下: +$$MMD^2(P_r,P_g)=E_{x_r\sim{P_r},x_g\sim{P_g}}[\lVert\Sigma_{i=1}^{n1}k(x_r)-\Sigma_{i=1}^{n2}k(x_g)\rVert]$$ +对于Kernel MMD值的计算,首先需要选择一个核函数$k$,这个核函数把样本映射到再生希尔伯特空间(Reproducing Kernel Hilbert Space, RKHS) ,RKHS相比于欧几里得空间有许多优点,对于函数内积的计算是完备的。将上述公式展开即可得到下面的计算公式: +$$MMD^2(P_r,P_g)=E_{x_r,x_r{'}\sim{P_r},x_g,x_g{'}\sim{P_g}}[k(x_r,x_r{'})-2k(x_r,x_g)+k(x_g,x_g{'})]$$ +MMD值越小,两个分布越接近。 + +**特点:可以一定程度上衡量模型生成图像的优劣性,计算代价小。推荐使用。** + +#### Wasserstein distance + +Wasserstein distance在最优传输问题中通常也叫做推土机距离。这个距离的介绍在WGAN中有详细讨论。公式如下: +$$WD(P_r,P_g)=min_{\omega\in\mathbb{R}^{m\times n}}\Sigma_{i=1}^n\Sigma_{i=1}^m\omega_{ij}d(x_i^r,x_j^g)$$ +$$s.t. \Sigma_{i=1}^mw_{i,j}=p_r(x_i^r), \forall i;\Sigma_{j=1}^nw_{i,j}=p_g(x_j^g), \forall j$$ +Wasserstein distance可以衡量两个分布之间的相似性。距离越小,分布越相似。 + +**特点:如果特征空间选择合适,会有一定的效果。但是计算复杂度为$O(n^3)​$太高** + +#### Fréchet Inception Distance (FID) + +FID距离计算真实样本,生成样本在特征空间之间的距离。首先利用Inception网络来提取特征,然后使用高斯模型对特征空间进行建模。根据高斯模型的均值和协方差来进行距离计算。具体公式如下: +$$FID(\mathbb P_r,\mathbb P_g)=\lVert\mu_r-\mu_g\rVert+Tr(C_r+C_g-2(C_rC_g)^{1/2})​$$ +$\mu,C​$分别代表协方差和均值。 + +**特点:尽管只计算了特征空间的前两阶矩,但是鲁棒,且计算高效。** + +#### 1-Nearest Neighbor classifier + +使用留一法,结合1-NN分类器(别的也行)计算真实图片,生成图像的精度。如果二者接近,则精度接近50%,否则接近0%。对于GAN的评价问题,作者分别用正样本的分类精度,生成样本的分类精度去衡量生成样本的真实性,多样性。 +- 对于真实样本$x_r$,进行1-NN分类的时候,如果生成的样本越真实。则真实样本空间$\mathbb R$将被生成的样本$x_g$包围。那么$x_r$的精度会很低。 +- 对于生成的样本$x_g$,进行1-NN分类的时候,如果生成的样本多样性不足。由于生成的样本聚在几个mode,则$x_g$很容易就和$x_r$区分,导致精度会很高。 + +**特点:理想的度量指标,且可以检测过拟合。** + +#### 其他评价方法 + +AIS,KDE方法也可以用于评价GAN,但这些方法不是model agnostic metrics。也就是说,这些评价指标的计算无法只利用:生成的样本,真实样本来计算。 + +### 7.1.6 其他常见的生成式模型有哪些? + +#### 什么是自回归模型:pixelRNN与pixelCNN? + +自回归模型通过对图像数据的概率分布$p_{data}(x)$进行显式建模,并利用极大似然估计优化模型。具体如下: +$$ +p_{data}(x)=\prod_{i=1}^np(x_i|x_1,x_2,...,x_{i-1}) +$$ +上述公式很好理解,给定$x_1,x_2,...,x_{i-1}$条件下,所有$p(x_i)$的概率乘起来就是图像数据的分布。如果使用RNN对上述依然关系建模,就是pixelRNN。如果使用CNN,则是pixelCNN。具体如下[5]: + +![](/Users/xfguo/Desktop/blog/zhihu/imgs/pixRNN.png) + +![](/Users/xfguo/Desktop/blog/zhihu/imgs/pixCNN.png) + +显然,不论是对于pixelCNN还是pixelRNN,由于其像素值是一个个生成的,速度会很慢。语音领域大火的WaveNet就是一个典型的自回归模型。 + +#### 什么是VAE? + +PixelCNN/RNN定义了一个易于处理的密度函数,我们可以直接优化训练数据的似然;对于变分自编码器我们将定义一个不易处理的密度函数,通过附加的隐变量$z​$对密度函数进行建模。 VAE原理图如下[6]: + +![](/Users/xfguo/Desktop/blog/zhihu/imgs/VAE.png) + +在VAE中,真实样本$X$通过神经网络计算出均值方差(假设隐变量服从正太分布),然后通过采样得到采样变量$Z$并进行重构。VAE和GAN均是学习了隐变量$z$到真实数据分布的映射。但是和GAN不同的是: + +- GAN的思路比较粗暴,使用一个判别器去度量分布转换模块(即生成器)生成分布与真实数据分布的距离。 +- VAE则没有那么直观,VAE通过约束隐变量$z$服从标准正太分布以及重构数据实现了分布转换映射$X=G(z)$ + +**生成式模型对比** + +- 自回归模型通过对概率分布显式建模来生成数据 +- VAE和GAN均是:假设隐变量$z$服从某种分布,并学习一个映射$X=G(z)$,实现隐变量分布$z$与真实数据分布$p_{data}(x)$的转换。 +- GAN使用判别器去度量映射$X=G(z)$的优劣,而VAE通过隐变量$z$与标准正太分布的KL散度和重构误差去度量。 + +## 7.2 GAN的改进 + +### 7.2.1 如何生成指定类型的图像——条件GAN + +条件生成对抗网络(CGAN, Conditional Generative Adversarial Networks)作为一个GAN的改进,其一定程度上解决了GAN生成结果的不确定性。如果在Mnist数据集上训练原始GAN,GAN生成的图像是完全不确定的,具体生成的是数字1,还是2,还是几,根本不可控。为了让生成的数字可控,我们可以把数据集做一个切分,把数字0~9的数据集分别拆分开训练9个模型,不过这样太麻烦了,也不现实。因为数据集拆分不仅仅是分类麻烦,更主要在于,每一个类别的样本少,拿去训练GAN很有可能导致欠拟合。因此,CGAN就应运而生了。我们先看一下CGAN的网络结构: +![CGAN网络结构](./img/ch7/CGAN网络结构.png) +从网络结构图可以看到,对于生成器Generator,其输入不仅仅是随机噪声的采样z,还有欲生成图像的标签信息。比如对于mnist数据生成,就是一个one-hot向量,某一维度为1则表示生成某个数字的图片。同样地,判别器的输入也包括样本的标签。这样就使得判别器和生成器可以学习到样本和标签之间的联系。Loss如下: +$$\mathop {\min }\limits_G \mathop {\max }\limits_D V(D,G) = {{\rm E}_{x\sim{p_{data}}(x)}}[\log D(x|y)] + {{\rm E}_{z\sim{p_z}(z)}}[\log (1 - D(G(z|y)))]$$ +Loss设计和原始GAN基本一致,只不过生成器,判别器的输入数据是一个条件分布。在具体编程实现时只需要对随机噪声采样z和输入条件y做一个级联即可。 + + + +### 7.2.3 CNN与GAN——DCGAN + +前面我们聊的GAN都是基于简单的神经网络构建的。可是对于视觉问题,如果使用原始的基于DNN的GAN,则会出现许多问题。如果输入GAN的随机噪声为100维的随机噪声,输出图像为256x256大小。也就是说,要将100维的信息映射为65536维。如果单纯用DNN来实现,那么整个模型参数会非常巨大,而且学习难度很大(低维度映射到高维度需要添加许多信息)。因此,DCGAN就出现了。具体而言,DCGAN将传统GAN的生成器,判别器均采用GAN实现,且使用了一下tricks: + +- 将pooling层convolutions替代,其中,在discriminator上用strided convolutions替代,在generator上用fractional-strided convolutions替代。 +- 在generator和discriminator上都使用batchnorm。 +- 移除全连接层,global pooling增加了模型的稳定性,但伤害了收敛速度。 +- 在generator的除了输出层外的所有层使用ReLU,输出层采用tanh。 +- 在discriminator的所有层上使用LeakyReLU。 + +网络结构图如下: +![CGAN网络结构图](./img/ch7/DCGAN%E7%BB%93%E6%9E%84%E5%9B%BE.png) + +#### 如何理解GAN中的输入随机噪声? + +为了了解输入随机噪声每一个维度代表的含义,作者做了一个非常有趣的工作。即在隐空间上,假设知道哪几个变量控制着某个物体,那么僵这几个变量挡住是不是就可以将生成图片中的某个物体消失?论文中的实验是这样的:首先,生成150张图片,包括有窗户的和没有窗户的,然后使用一个逻辑斯底回归函数来进行分类,对于权重不为0的特征,认为它和窗户有关。将其挡住,得到新的生成图片,结果如下: +![DCGAN输入噪声理解](./img/ch7/DCGAN%E8%BE%93%E5%85%A5%E5%99%AA%E5%A3%B0%E7%90%86%E8%A7%A3.png) +此外,将几个输入噪声进行算数运算,可以得到语义上进行算数运算的非常有趣的结果。类似于word2vec。 +![DCGAN输入噪声算术运算](./img/ch7/DCGAN%E8%BE%93%E5%85%A5%E5%99%AA%E5%A3%B0%E7%AE%97%E6%9C%AF%E8%BF%90%E7%AE%97.png) + +### 7.2.4 如何度量GAN的收敛程度?——WGAN/WGAN-GP + +#### GAN为什么容易训练崩溃? + +所谓GAN的训练崩溃,指的是训练过程中,生成器和判别器存在一方压倒另一方的情况。 +GAN原始判别器的Loss在判别器达到最优的时候,等价于最小化生成分布与真实分布之间的JS散度,由于随机生成分布很难与真实分布有不可忽略的重叠以及JS散度的突变特性,使得生成器面临梯度消失的问题;可是如果不把判别器训练到最优,那么生成器优化的目标就失去了意义。因此需要我们小心的平衡二者,要把判别器训练的不好也不坏才行。否则就会出现训练崩溃,得不到想要的结果 + +#### WGAN如何解决训练崩溃问题? + +WGAN作者提出了使用Wasserstein距离,以解决GAN网络训练过程难以判断收敛性的问题。Wasserstein距离定义如下: +$$L={{\rm E}_{x\sim{p_{data}}(x)}}[f_w(x)] - {{\rm E}_{x\sim{p_g}(x)}}[f_w(x)]$$ +通过最小化Wasserstein距离,得到了WGAN的Loss: + +- WGAN生成器Loss:$- {{\rm E}_{x\sim{p_g}(x)}}[f_w(x)]$ +- WGAN判别器Loss:$L=-{{\rm E}_{x\sim{p_{data}}(x)}}[f_w(x)] + {{\rm E}_{x\sim{p_g}(x)}}[f_w(x)]$ + +从公式上GAN似乎总是让人摸不着头脑,在代码实现上来说,其实就以下几点: + +- 判别器最后一层去掉sigmoid +- 生成器和判别器的loss不取log +- 每次更新判别器的参数之后把它们的绝对值截断到不超过一个固定常数c + +#### WGAN-GP:带有梯度正则的WGAN + +实际实验过程发现,WGAN没有那么好用,主要原因在于WAGN进行梯度截断。梯度截断将导致判别网络趋向于一个二值网络,造成模型容量的下降。 +于是作者提出使用梯度惩罚来替代梯度裁剪。公式如下: +$$L=-{{\rm E}_{x\sim{p_{data}}(x)}}[f_w(x)] + {{\rm E}_{x\sim{p_g}(x)}}[f_w(x)]+\lambda{{\rm E}_{x\sim{p_x}(x)}}[\lVert\nabla_x(D(x))\rVert_p-1]^2$$ +由于上式是对每一个梯度进行惩罚,所以不适合使用BN,因为它会引入同个batch中不同样本的相互依赖关系。如果需要的话,可以选择Layer Normalization。实际训练过程中,就可以通过Wasserstein距离来度量模型收敛程度了: +![Wass距离随迭代次数变化](./img/ch7/Wass%E8%B7%9D%E7%A6%BB%E9%9A%8F%E8%BF%AD%E4%BB%A3%E6%AC%A1%E6%95%B0%E5%8F%98%E5%8C%96.png) +上图纵坐标是Wasserstein距离,横坐标是迭代次数。可以看出,随着迭代的进行,Wasserstein距离趋于收敛,生成图像也趋于稳定。 + +### 7.2.5 LSGAN + +LSGAN(Least Squares GAN)这篇文章主要针对标准GAN的稳定性和图片生成质量不高做了一个改进。作者将原始GAN的交叉熵损失采用最小二乘损失替代。LSGAN的Loss: +$$\mathop{\min }\limits_DJ(D)=\mathop{\min}\limits_D[{\frac{1}{2}}{{\rm E}_{x\sim{p_{data}}(x)}}[D(x)-a]^2 + {\frac{1}{2}}{{\rm E}_{z\sim{p_z}(z)}}[D(G(z))-b]^2]$$ +$$\mathop{\min }\limits_GJ(G)=\mathop{\min}\limits_G{\frac{1}{2}}{{\rm E}_{z\sim{p_z}(z)}}[D(G(z))-c]^2$$ +实际实现的时候非常简单,最后一层去掉sigmoid,并且计算Loss的时候用平方误差即可。之所以这么做,作者在原文给出了一张图: +![LSGAN交叉熵与最小二乘损失对比图](./img/ch7/LSGAN%E4%BA%A4%E5%8F%89%E7%86%B5%E4%B8%8E%E6%9C%80%E5%B0%8F%E4%BA%8C%E4%B9%98%E6%8D%9F%E5%A4%B1%E5%AF%B9%E6%AF%94%E5%9B%BE.png) +上面是作者给出的基于交叉熵损失以及最小二乘损失的Loss函数。横坐标代表Loss函数的输入,纵坐标代表输出的Loss值。可以看出,随着输入的增大,sigmoid交叉熵损失很快趋于0,容易导致梯度饱和问题。如果使用右边的Loss设计,则只在x=0点处饱和。因此使用LSGAN可以很好的解决交叉熵损失的问题。 + +### 7.2.6 如何尽量避免GAN的训练崩溃问题? + +- 归一化图像输入到(-1,1)之间;Generator最后一层使用tanh激活函数 +- 生成器的Loss采用:min (log 1-D)。因为原始的生成器Loss存在梯度消失问题;训练生成器的时候,考虑反转标签,real=fake, fake=real +- 不要在均匀分布上采样,应该在高斯分布上采样 +- 一个Mini-batch里面必须只有正样本,或者负样本。不要混在一起;如果用不了Batch Norm,可以用Instance Norm +- 避免稀疏梯度,即少用ReLU,MaxPool。可以用LeakyReLU替代ReLU,下采样可以用Average Pooling或者Convolution + stride替代。上采样可以用PixelShuffle, ConvTranspose2d + stride +- 平滑标签或者给标签加噪声;平滑标签,即对于正样本,可以使用0.7-1.2的随机数替代;对于负样本,可以使用0-0.3的随机数替代。 给标签加噪声:即训练判别器的时候,随机翻转部分样本的标签。 +- 如果可以,请用DCGAN或者混合模型:KL+GAN,VAE+GAN。 +- 使用LSGAN,WGAN-GP +- Generator使用Adam,Discriminator使用SGD +- 尽快发现错误;比如:判别器Loss为0,说明训练失败了;如果生成器Loss稳步下降,说明判别器没发挥作用 +- 不要试着通过比较生成器,判别器Loss的大小来解决训练过程中的模型坍塌问题。比如: + While Loss D > Loss A: + Train D + While Loss A > Loss D: + Train A +- 如果有标签,请尽量利用标签信息来训练 +- 给判别器的输入加一些噪声,给G的每一层加一些人工噪声。 +- 多训练判别器,尤其是加了噪声的时候 +- 对于生成器,在训练,测试的时候使用Dropout + +## 7.3 GAN的应用 + +### 7.3.1 什么是图像翻译? +GAN作为一种强有力的生成模型,其应用十分广泛。最为常见的应用就是图像翻译。所谓图像翻译,指从一副图像到另一副图像的转换。可以类比机器翻译,一种语言转换为另一种语言。常见的图像翻译任务有: +- 图像去噪 +- 图像超分辨 +- 图像补全 +- 风格迁移 +- ... + +本节将介绍一个经典的图像翻译网络及其改进。图像翻译可以分为有监督图像翻译和无监督图像翻译: +- 有监督图像翻译:原始域与目标域存在一一对应数据 +- 无监督图像翻译:原始域与目标域不存在一一对应数据 +### 7.3.2 有监督图像翻译:pix2pix +在这篇paper里面,作者提出的框架十分简洁优雅(好用的算法总是简洁优雅的)。相比以往算法的大量专家知识,手工复杂的loss。这篇paper非常粗暴,使用CGAN处理了一系列的转换问题。下面是一些转换示例: +![pix2pix结果示例](./img/ch7/pix2pix结果示例.png) + +上面展示了许多有趣的结果,比如分割图$\longrightarrow$街景图,边缘图$\longrightarrow$真实图。对于第一次看到的时候还是很惊艳的,那么这个是怎么做到的呢?我们可以设想一下,如果是我们,我们自己会如何设计这个网络? + +#### 直观的想法? +最直接的想法就是,设计一个CNN网络,直接建立输入-输出的映射,就像图像去噪问题一样。可是对于上面的问题,这样做会带来一个问题。**生成图像质量不清晰。** + +拿左上角的分割图$\longrightarrow$街景图为例,语义分割图的每个标签比如“汽车”可能对应不同样式,颜色的汽车。那么模型学习到的会是所有不同汽车的评均,这样会造成模糊。![pix2pix语义地图L1loss结果](./img/ch7/pix2pix语义地图L1loss结果.png) + + +#### 如何解决生成图像的模糊问题? +这里作者想了一个办法,即加入GAN的Loss去惩罚模型。GAN相比于传统生成式模型可以较好的生成高分辨率图片。思路也很简单,在上述直观想法的基础上加入一个判别器,判断输入图片是否是真实样本。模型示意图如下: +![pix2pix模型示意图](./img/ch7/pix2pix模型示意图.png) + + +上图模型和CGAN有所不同,但它是一个CGAN,只不过输入只有一个,这个输入就是条件信息。原始的CGAN需要输入随机噪声,以及条件。这里之所有没有输入噪声信息,是因为在实际实验中,如果输入噪声和条件,噪声往往被淹没在条件C当中,所以这里直接省去了。 + +#### 其他图像翻译的tricks +从上面两点可以得到最终的Loss由两部分构成: +- 输出和标签信息的L1 Loss。 +- GAN Loss +- 测试也使用Dropout,以使输出多样化 +![pix2pix Loss](./img/ch7/pix2pix_Loss.png) + +采用L1 Loss而不是L2 Loss的理由很简单,L1 Loss相比于L2 Loss保边缘(L2 Loss基于高斯先验,L1 Loss基于拉普拉斯先验)。 + +GAN Loss为LSGAN的最小二乘Loss,并使用PatchGAN(进一步保证生成图像的清晰度)。PatchGAN将图像换分成很多个Patch,并对每一个Patch使用判别器进行判别(实际代码实现有更取巧的办法),将所有Patch的Loss求平均作为最终的Loss。 + +#### 如何生成高分辨率图像和高分辨率视频? + +pix2pix提出了一个通用的图像翻译框架。对于高分辨率的图像生成以及高分辨率的视频生成,则需要利用更好的网络结构以及更多的先验只是。pix2pixHD提出了一种多尺度的生成器以及判别器等方式从而生成高分辨率图像。Vid2Vid则在pix2pixHD的基础上利用光流,时序约束生成了高分辨率视频。 + +### 7.3.3 有监督的图像翻译的缺点? +许多图像翻译算法如前面提及的pix2pix系列,需要一一对应的图像。可是在许多应用场景下,往往没有这种一一对应的强监督信息。比如说以下一些应用场景: +![CycleGAN结果例子](./img/ch7/CycleGAN结果例子.png) +以第一排第一幅图为例,要找到这种一一配对的数据是不现实的。因此,无监督图像翻译算法就被引入了。 + +### 7.3.4 无监督图像翻译:CycleGAN +#### 模型结构 +总体思路如下,假设有两个域的数据,记为A,B。对于上图第一排第一幅图A域就是普通的马,B域就是斑马。由于A->B的转换缺乏监督信息,于是,作者提出采用如下方法进行转换: +>a. A->fake_B->rec_A +b. B->fake_A->rec_B + +对于A域的所有图像,学习一个网络G_B,该网络可以生成B。对于B域的所有图像,也学习一个网络G_A,该网络可以生成G_B。 + +训练过程分成两步,首先对于A域的某张图像,送入G_B生成fake_B,然后对fake_B送入G_A,得到重构后的A图像rec_A。对于B域的某一张图像也是类似。重构后的图像rec_A/rec_B可以和原图A/B做均方误差,实现了有监督的训练。此处值得注意的是A->fake_B(B->fake_A)和fake_A->rec_B(fake_B->rec_A)的网络是一模一样的。下图是形象化的网络结构图: +![CycleGAN模型示意图](./img/ch7/CycleGAN模型示意图.png) +cycleGAN的生成器采用U-Net,判别器采用LS-GAN。 + +#### Loss设计 +总的Loss就是X域和Y域的GAN Loss,以及Cycle consistency loss: +$$L(G,F,D_X,D_Y)=L_{GAN}(G,D_Y,X,Y)+L_{GAN}(F,D_X,Y,X)+\lambda L_{cycle}(G,F)$$ +整个过程End to end训练,效果非常惊艳,利用这一框架可以完成非常多有趣的任务 + +#### 多领域的无监督图像翻译:StarGAN + +cycleGAN模型较好的解决了无监督图像转换问题,可是这种单一域的图像转换还存在一些问题: + +- 要针对每一个域训练一个模型,效率太低。举例来说,我希望可以将橘子转换为红苹果和青苹果。对于cycleGAN而言,需要针对红苹果,青苹果分别训练一个模型。 +- 对于每一个域都需要搜集大量数据,太麻烦。还是以橘子转换为红苹果和青苹果为例。不管是红苹果还是青苹果,都是苹果,只是颜色不一样而已。这两个任务信息是可以共享的,没必要分别训练两个模型。而且针对红苹果,青苹果分别取搜集大量数据太费事。 + +starGAN则提出了一个多领域的无监督图像翻译框架,实现了多个领域的图像转换,且对于不同领域的数据可以混合在一起训练,提高了数据利用率 + +### 7.3.5 GAN在文本生成领域中的应用:SeqGAN + +#### GAN为什么不适合文本任务? + +GAN在2014年被提出之后,在图像生成领域取得了广泛的研究应用。然后在文本领域却一直没有很惊艳的效果。主要在于文本数据是离散数据,而GAN在应用于离散数据时存在以下几个问题: + +- GAN的生成器梯度来源于判别器对于正负样本的判别。然而,对于文本生成问题,RNN输出的是一个概率序列,然后取argmax。这会导致生成器Loss不可导。还可以站在另一个角度理解,由于是argmax,所以参数更新一点点并不会改变argmax的结果,这也使得GAN不适合离散数据。 +- GAN只能评估整个序列的loss,但是无法评估半句话,或者是当前生成单词对后续结果好坏的影响。 +- 如果不加argmax,那么由于生成器生成的都是浮点数值,而ground truth都是one-hot encoding,那么判别器只要判别生成的结果是不是0/1序列组成的就可以了。这容易导致训练崩溃。 + +#### seqGAN用于文本生成 + +seqGAN在GAN的框架下,结合强化学习来做文本生成。 模型示意图如下: + +![seqGAN模型](./img/ch7/seqGAN模型.png) +在文本生成任务,seqGAN相比较于普通GAN区别在以下几点: + +- 生成器不取argmax。 +- 每生成一个单词,则根据当前的词语序列进行蒙特卡洛采样生成完成的句子。然后将句子送入判别器计算reward。 +- 根据得到的reward进行策略梯度下降优化模型。 + +### 7.3.6 GAN在其他领域的应用 + +#### 数据增广 + +GAN的良好生成特性近年来也开始被用于数据增广。以行人重识别为例,有许多GAN用于数据增广[^ 1][^2][^ 3][^ 4]的工作。行人重识别问题一个难点在于不同摄像头下拍摄的人物环境,角度差别非常大,导致存在较大的Domain gap。因此,可以考虑使用GAN来产生不同摄像头下的数据进行数据增广。以论文[^ 1]为例,本篇paper提出了一个cycleGAN用于数据增广的方法。具体模型结构如下: + +![cycleGAN数据增广](./img/ch7/cycleGAN数据增广.png) + +对于每一对摄像头都训练一个cycleGAN,这样就可以实现将一个摄像头下的数据转换成另一个摄像头下的数据,但是内容(人物)保持不变。 + +#### 图像超分辨与图像补全 + +图像超分辨与补全均可以作为图像翻译问题,该类问题的处理办法也大都是训练一个端到端的网络,输入是原始图片,输出是超分辨率后的图片,或者是补全后的图片。SRGAN[^ 5]利用GAN作为判别器,使得超分辨率模型输出的图片更加清晰,更符合人眼主管感受。日本早稻田大学研究人员[^ 6]提出一种全局+局部一致性的GAN实现图像补全,使得修复后的图像不仅细节清晰,且具有整体一致性。 + +#### 语音领域 + +相比于图像领域遍地开花,GAN在语音领域则应用相对少了很多。这里零碎的找一些GAN在语音领域进行应用的例子作为介绍。Pascual[^ 7]提出了一种音频去噪的SEGAN,缓解了传统方法支持噪声种类稀少,泛化能力不强的问题。Donahue利用GAN进行语音增强,提升了ASR系统的识别率。 + +---------- + +[^ 1]: Zheng Z , Zheng L , Yang Y . Unlabeled Samples Generated by GAN Improve the Person Re-identification Baseline in Vitro[C]// 2017 IEEE International Conference on Computer Vision (ICCV). IEEE Computer Society, 2017. +[^ 2]: Zhong Z , Zheng L , Zheng Z , et al. Camera Style Adaptation for Person Re-identification[J]. 2017. +[^ 3]: Deng W , Zheng L , Ye Q , et al. Image-Image Domain Adaptation with Preserved Self-Similarity and Domain-Dissimilarity for Person Re-identification[J]. 2017. +[^4]: Wei L , Zhang S , Gao W , et al. Person Transfer GAN to Bridge Domain Gap for Person Re-Identification[J]. 2017. +[^ 5]: Ledig C , Theis L , Huszar F , et al. Photo-Realistic Single Image Super-Resolution Using a Generative Adversarial Network[J]. 2016. +[^ 6]: Ishikawa H, Ishikawa H, Ishikawa H. Globally and locally consistent image completion[M]. 2017. +[^7]: Pascual S , Bonafonte A , Serrà, Joan. SEGAN: Speech Enhancement Generative Adversarial Network[J]. 2017. +[^ 8]: Donahue C , Li B , Prabhavalkar R . Exploring Speech Enhancement with Generative Adversarial Networks for Robust Speech Recognition[J]. 2017. + diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch7.pdf" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch7.pdf" new file mode 100644 index 00000000..25689f2b Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch7.pdf" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/7.1-gan_structure.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/7.1-gan_structure.png" similarity index 100% rename from "ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/7.1-gan_structure.png" rename to "ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/7.1-gan_structure.png" diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/Boundary_map.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/Boundary_map.png" similarity index 100% rename from "ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/Boundary_map.png" rename to "ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/Boundary_map.png" diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/CGAN\347\275\221\347\273\234\347\273\223\346\236\204.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/CGAN\347\275\221\347\273\234\347\273\223\346\236\204.png" similarity index 100% rename from "ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/CGAN\347\275\221\347\273\234\347\273\223\346\236\204.png" rename to "ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/CGAN\347\275\221\347\273\234\347\273\223\346\236\204.png" diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/CycleGAN\346\250\241\345\236\213\347\244\272\346\204\217\345\233\276.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/CycleGAN\346\250\241\345\236\213\347\244\272\346\204\217\345\233\276.png" new file mode 100644 index 00000000..4af9d521 Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/CycleGAN\346\250\241\345\236\213\347\244\272\346\204\217\345\233\276.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/CycleGAN\347\273\223\346\236\234\344\276\213\345\255\220.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/CycleGAN\347\273\223\346\236\234\344\276\213\345\255\220.png" new file mode 100644 index 00000000..984f3177 Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/CycleGAN\347\273\223\346\236\234\344\276\213\345\255\220.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/DCGAN\347\273\223\346\236\204\345\233\276.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/DCGAN\347\273\223\346\236\204\345\233\276.png" new file mode 100644 index 00000000..9a14e9ca Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/DCGAN\347\273\223\346\236\204\345\233\276.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/DCGAN\350\276\223\345\205\245\345\231\252\345\243\260\347\220\206\350\247\243.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/DCGAN\350\276\223\345\205\245\345\231\252\345\243\260\347\220\206\350\247\243.png" new file mode 100644 index 00000000..7d88f093 Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/DCGAN\350\276\223\345\205\245\345\231\252\345\243\260\347\220\206\350\247\243.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/DCGAN\350\276\223\345\205\245\345\231\252\345\243\260\347\256\227\346\234\257\350\277\220\347\256\227.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/DCGAN\350\276\223\345\205\245\345\231\252\345\243\260\347\256\227\346\234\257\350\277\220\347\256\227.png" new file mode 100644 index 00000000..d07fbf23 Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/DCGAN\350\276\223\345\205\245\345\231\252\345\243\260\347\256\227\346\234\257\350\277\220\347\256\227.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/LSGAN\344\272\244\345\217\211\347\206\265\344\270\216\346\234\200\345\260\217\344\272\214\344\271\230\346\215\237\345\244\261\345\257\271\346\257\224\345\233\276.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/LSGAN\344\272\244\345\217\211\347\206\265\344\270\216\346\234\200\345\260\217\344\272\214\344\271\230\346\215\237\345\244\261\345\257\271\346\257\224\345\233\276.png" new file mode 100644 index 00000000..18c7fc63 Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/LSGAN\344\272\244\345\217\211\347\206\265\344\270\216\346\234\200\345\260\217\344\272\214\344\271\230\346\215\237\345\244\261\345\257\271\346\257\224\345\233\276.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/Wass\350\267\235\347\246\273\351\232\217\350\277\255\344\273\243\346\254\241\346\225\260\345\217\230\345\214\226.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/Wass\350\267\235\347\246\273\351\232\217\350\277\255\344\273\243\346\254\241\346\225\260\345\217\230\345\214\226.png" new file mode 100644 index 00000000..a2205ddf Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/Wass\350\267\235\347\246\273\351\232\217\350\277\255\344\273\243\346\254\241\346\225\260\345\217\230\345\214\226.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/cycleGAN\346\225\260\346\215\256\345\242\236\345\271\277.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/cycleGAN\346\225\260\346\215\256\345\242\236\345\271\277.png" new file mode 100644 index 00000000..fdb8b520 Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/cycleGAN\346\225\260\346\215\256\345\242\236\345\271\277.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/mode_dropping.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/mode_dropping.png" new file mode 100644 index 00000000..de9feadb Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/mode_dropping.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/model_collpsing.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/model_collpsing.png" new file mode 100644 index 00000000..6900aaac Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/model_collpsing.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/pix2pixHD_Loss.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/pix2pixHD_Loss.png" similarity index 100% rename from "ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/pix2pixHD_Loss.png" rename to "ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/pix2pixHD_Loss.png" diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/pix2pixHD\347\275\221\347\273\234\347\273\223\346\236\204.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/pix2pixHD\347\275\221\347\273\234\347\273\223\346\236\204.png" similarity index 100% rename from "ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/pix2pixHD\347\275\221\347\273\234\347\273\223\346\236\204.png" rename to "ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/pix2pixHD\347\275\221\347\273\234\347\273\223\346\236\204.png" diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/pix2pix_Loss.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/pix2pix_Loss.png" similarity index 100% rename from "ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/pix2pix_Loss.png" rename to "ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/pix2pix_Loss.png" diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/pix2pix\346\250\241\345\236\213\347\244\272\346\204\217\345\233\276.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/pix2pix\346\250\241\345\236\213\347\244\272\346\204\217\345\233\276.png" similarity index 100% rename from "ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/pix2pix\346\250\241\345\236\213\347\244\272\346\204\217\345\233\276.png" rename to "ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/pix2pix\346\250\241\345\236\213\347\244\272\346\204\217\345\233\276.png" diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/pix2pix\347\273\223\346\236\234\347\244\272\344\276\213.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/pix2pix\347\273\223\346\236\234\347\244\272\344\276\213.png" similarity index 100% rename from "ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/pix2pix\347\273\223\346\236\234\347\244\272\344\276\213.png" rename to "ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/pix2pix\347\273\223\346\236\234\347\244\272\344\276\213.png" diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/pix2pix\350\257\255\344\271\211\345\234\260\345\233\276L1loss\347\273\223\346\236\234.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/pix2pix\350\257\255\344\271\211\345\234\260\345\233\276L1loss\347\273\223\346\236\234.png" similarity index 100% rename from "ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/pix2pix\350\257\255\344\271\211\345\234\260\345\233\276L1loss\347\273\223\346\236\234.png" rename to "ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/pix2pix\350\257\255\344\271\211\345\234\260\345\233\276L1loss\347\273\223\346\236\234.png" diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/readme.md" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/readme.md" similarity index 100% rename from "ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/readme.md" rename to "ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/readme.md" diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/seqGAN\346\250\241\345\236\213.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/seqGAN\346\250\241\345\236\213.png" new file mode 100644 index 00000000..91ace026 Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/seqGAN\346\250\241\345\236\213.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/starGAN\345\212\240\345\205\245mask\347\244\272\346\204\217\345\233\276.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/starGAN\345\212\240\345\205\245mask\347\244\272\346\204\217\345\233\276.png" new file mode 100644 index 00000000..0cd5d1f4 Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/starGAN\345\212\240\345\205\245mask\347\244\272\346\204\217\345\233\276.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/starGAN\346\250\241\345\236\213\347\273\223\346\236\204.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/starGAN\346\250\241\345\236\213\347\273\223\346\236\204.png" new file mode 100644 index 00000000..22ad0222 Binary files /dev/null and "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/starGAN\346\250\241\345\236\213\347\273\223\346\236\204.png" differ diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/upsample.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/upsample.png" similarity index 100% rename from "ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/upsample.png" rename to "ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/upsample.png" diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/\350\257\255\344\271\211\347\274\226\350\276\221.png" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/\350\257\255\344\271\211\347\274\226\350\276\221.png" similarity index 100% rename from "ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/\350\257\255\344\271\211\347\274\226\350\276\221.png" rename to "ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/img/ch7/\350\257\255\344\271\211\347\274\226\350\276\221.png" diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/modify_log.txt" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/modify_log.txt" deleted file mode 100644 index c5e0e582..00000000 --- "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/modify_log.txt" +++ /dev/null @@ -1,20 +0,0 @@ -该文件用来记录修改日志: -<----shw2018-2018-10-25----> -1. 新增章节markdown文件 - -<----shw2018-2018-10-28----> -1. 修改错误内容和格式 -2. 修改图片路径 - -<----shw2018-2018-10-31----> -1. 新增第九章文件夹,里面包括: -img---->用来放对应章节图片,例如路径./img/ch9/ch_* -readme.md---->章节维护贡献者信息 -modify_log---->用来记录修改日志 -第 * 章_xxx.md---->对应章节markdown文件 -第 * 章_xxx.pdf---->对应章节生成pdf文件,便于阅读 -其他---->待增加 -2. 修改readme内容 -3. 修改modify内容 -4. 修改章节内容,图片路径等 - diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/readme.md" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/readme.md" deleted file mode 100644 index 5e5d42b4..00000000 --- "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/readme.md" +++ /dev/null @@ -1,13 +0,0 @@ -########################################################### - -### 深度学习500问-第 * 章 xxx - -**负责人(排名不分先后):** -牛津大学博士生-程泽华 -中科院研究生-郭晓锋 - - -**贡献者(排名不分先后):** -内容贡献者可自加信息 - -########################################################### diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ref.bib" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ref.bib" deleted file mode 100644 index 86d0508a..00000000 --- "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/ref.bib" +++ /dev/null @@ -1,66 +0,0 @@ -@article{arjovsky2017towards, - title={Towards principled methods for training generative adversarial networks}, - author={Arjovsky, Martin and Bottou, L{\'e}on}, - journal={arXiv preprint arXiv:1701.04862}, - year={2017} -} -@inproceedings{nowozin2016f, - title={f-gan: Training generative neural samplers using variational divergence minimization}, - author={Nowozin, Sebastian and Cseke, Botond and Tomioka, Ryota}, - booktitle={Advances in Neural Information Processing Systems}, - pages={271--279}, - year={2016} -} -@article{choi2017stargan, - title={Stargan: Unified generative adversarial networks for multi-domain image-to-image translation}, - author={Choi, Yunjey and Choi, Minje and Kim, Munyoung and Ha, Jung-Woo and Kim, Sunghun and Choo, Jaegul}, - journal={arXiv preprint}, - volume={1711}, - year={2017} -} -@article{isola2017image, - title={Image-to-image translation with conditional adversarial networks}, - author={Isola, Phillip and Zhu, Jun-Yan and Zhou, Tinghui and Efros, Alexei A}, - journal={arXiv preprint}, - year={2017} -} -@article{radford2015unsupervised, - title={Unsupervised representation learning with deep convolutional generative adversarial networks}, - author={Radford, Alec and Metz, Luke and Chintala, Soumith}, - journal={arXiv preprint arXiv:1511.06434}, - year={2015} -} -@inproceedings{long2015fully, - title={Fully convolutional networks for semantic segmentation}, - author={Long, Jonathan and Shelhamer, Evan and Darrell, Trevor}, - booktitle={Proceedings of the IEEE conference on computer vision and pattern recognition}, - pages={3431--3440}, - year={2015} -} -@article{murez2017image, - title={Image to image translation for domain adaptation}, - author={Murez, Zak and Kolouri, Soheil and Kriegman, David and Ramamoorthi, Ravi and Kim, Kyungnam}, - journal={arXiv preprint arXiv:1712.00479}, - volume={13}, - year={2017} -} -@inproceedings{yi2017dualgan, - title={DualGAN: Unsupervised Dual Learning for Image-to-Image Translation.}, - author={Yi, Zili and Hao (Richard) Zhang and Tan, Ping and Gong, Minglun}, - booktitle={ICCV}, - pages={2868--2876}, - year={2017} -} -@inproceedings{wu2018wasserstein, - title={Wasserstein Divergence for GANs}, - author={Wu, Jiqing and Huang, Zhiwu and Thoma, Janine and Acharya, Dinesh and Van Gool, Luc}, - booktitle={Proceedings of the European Conference on Computer Vision (ECCV)}, - pages={653--668}, - year={2018} -} -@article{zhu2017unpaired, - title={Unpaired image-to-image translation using cycle-consistent adversarial networks}, - author={Zhu, Jun-Yan and Park, Taesung and Isola, Phillip and Efros, Alexei A}, - journal={arXiv preprint}, - year={2017} -} \ No newline at end of file diff --git "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/\347\254\254\344\270\203\347\253\240_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN).md" "b/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/\347\254\254\344\270\203\347\253\240_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN).md" deleted file mode 100644 index 11783080..00000000 --- "a/ch07_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN)/\347\254\254\344\270\203\347\253\240_\347\224\237\346\210\220\345\257\271\346\212\227\347\275\221\347\273\234(GAN).md" +++ /dev/null @@ -1,403 +0,0 @@ - -# -# 7.1 什么是生成对抗网络 -## GAN的通俗化介绍 - -生成对抗网络(GAN, Generative adversarial network)自从2014年被Ian Goodfellow提出以来,掀起来了一股研究热潮。GAN由生成器和判别器组成,生成器负责生成样本,判别器负责判断生成器生成的样本是否为真。生成器要尽可能迷惑判别器,而判别器要尽可能区分生成器生成的样本和真实样本。 - -在GAN的原作[1]中,作者将生成器比喻为印假钞票的犯罪分子,判别器则类比为警察。犯罪分子努力让钞票看起来逼真,警察则不断提升对于假钞的辨识能力。二者互相博弈,随着时间的进行,都会越来越强。 - -## GAN的形式化表达 -上述例子只是简要介绍了一下GAN的思想,下面对于GAN做一个形式化的,更加具体的定义。通常情况下,无论是生成器还是判别器,我们都可以用神经网络来实现。那么,我们可以把通俗化的定义用下面这个模型来表示: -![GAN网络结构](./img/ch7/7.1-gan_structure.png) - -上述模型左边是生成器G,其输入是$z$,对于原始的GAN,$z$是由高斯分布随机采样得到的噪声。噪声$z$通过生成器得到了生成的假样本。 - -生成的假样本与真实样本放到一起,被随机抽取送入到判别器D,由判别器去区分输入的样本是生成的假样本还是真实的样本。整个过程简单明了,生成对抗网络中的“生成对抗”主要体现在生成器和判别器之间的对抗。 - -## GAN的目标函数 -对于上述神经网络模型,如果想要学习其参数,首先需要一个目标函数。GAN的目标函数定义如下: - -$$\mathop {\min }\limits_G \mathop {\max }\limits_D V(D,G) = {{\rm E}_{x\sim{p_{data}}(x)}}[\log D(x)] + {{\rm E}_{z\sim{p_z}(z)}}[\log (1 - D(G(z)))]$$ - -这个目标函数可以分为两个部分来理解: - -判别器的优化通过$\mathop {\max}\limits_D V(D,G)$实现,$V(D,G)$为判别器的目标函数,其第一项${{\rm E}_{x\sim{p_{data}}(x)}}[\log D(x)]$表示对于从真实数据分布 中采用的样本 ,其被判别器判定为真实样本概率的数学期望。对于真实数据分布 中采样的样本,其预测为正样本的概率当然是越接近1越好。因此希望最大化这一项。第二项${{\rm E}_{z\sim{p_z}(z)}}[\log (1 - D(G(z)))]$表示:对于从噪声P_z(z)分布当中采样得到的样本经过生成器生成之后得到的生成图片,然后送入判别器,其预测概率的负对数的期望,这个值自然是越大越好,这个值越大, 越接近0,也就代表判别器越好。 - -生成器的优化通过$\mathop {\min }\limits_G({\mathop {\max }\limits_D V(D,G)})$实现。注意,生成器的目标不是$\mathop {\min }\limits_GV(D,G)$,即生成器**不是最小化判别器的目标函数**,生成器最小化的是**判别器目标函数的最大值**,判别器目标函数的最大值代表的是真实数据分布与生成数据分布的JS散度(详情可以参阅附录的推导),JS散度可以度量分布的相似性,两个分布越接近,JS散度越小。 - - -## GAN的目标函数和交叉熵 -判别器目标函数写成离散形式即为$$V(D,G)=-\frac{1}{m}\sum_{i=1}^{i=m}logD(x^i)-\frac{1}{m}\sum_{i=1}^{i=m}log(1-D(\tilde{x}^i))$$ -可以看出,这个目标函数和交叉熵是一致的,即**判别器的目标是最小化交叉熵损失,生成器的目标是最小化生成数据分布和真实数据分布的JS散度** - - -------------------- -[1]: Goodfellow, Ian, et al. "Generative adversarial nets." Advances in neural information processing systems. 2014. - -# 7.2 什么是图像翻译 -GAN作为一种强有力的生成模型,其应用十分广泛。最为常见的应用就是图像翻译。所谓图像翻译,指从一副图像到另一副图像的转换。可以类比机器翻译,一种语言转换为另一种语言。常见的图像翻译任务有: -- 图像去噪 -- 图像超分辨 -- 图像补全 -- 风格迁移 -- ... - -本节将介绍一个经典的图像翻译网络及其改进。 -# 7.2.1 pix2pix:图像翻译 -在这篇paper里面,作者提出的框架十分简洁优雅(好用的算法总是简洁优雅的)。相比以往算法的大量专家知识,手工复杂的loss。这篇paper非常粗暴,使用CGAN处理了一系列的转换问题。下面是一些转换示例: -![pix2pix结果示例](./img/ch7/pix2pix结果示例.png) - -上面展示了许多有趣的结果,比如分割图$\longrightarrow$街景图,边缘图$\longrightarrow$真实图。对于第一次看到的时候还是很惊艳的,那么这个是怎么做到的呢?我们可以设想一下,如果是我们,我们自己会如何设计这个网络。 - -## 如何做图像翻译? -最直接的想法就是,设计一个CNN网络,直接建立输入-输出的映射,就像图像去噪问题一样。可是对于上面的问题,这样做会带来一个问题。**生成图像质量不清晰。** - -拿左上角的分割图$\longrightarrow$街景图为例,语义分割图的每个标签比如“汽车”可能对应不同样式,颜色的汽车。那么模型学习到的会是所有不同汽车的评均,这样会造成模糊。![pix2pix语义地图L1loss结果](./img/ch7/pix2pix语义地图L1loss结果.png) - - -## 如何解决模糊呢? -这里作者想了一个办法,即加入GAN的Loss去惩罚模型。GAN相比于传统生成式模型可以较好的生成高分辨率图片。思路也很简单,在上述直观想法的基础上加入一个判别器,判断输入图片是否是真实样本。模型示意图如下: -![pix2pix模型示意图](./img/ch7/pix2pix模型示意图.png) - - -上图模型和CGAN有所不同,但它是一个CGAN,只不过输入只有一个,这个输入就是条件信息。原始的CGAN需要输入随机噪声,以及条件。这里之所有没有输入噪声信息,是因为在实际实验中,如果输入噪声和条件,噪声往往被淹没在条件C当中,所以这里直接省去了。 - -## 图像翻译的tricks -从上面两点可以得到最终的Loss由两部分构成: -- 输出和标签信息的L1 Loss。 -- GAN Loss -- 测试也使用Dropout,以使输出多样化 -![pix2pix Loss](./img/ch7/pix2pix_Loss.png) - -采用L1 Loss而不是L2 Loss的理由很简单,L1 Loss相比于L2 Loss保边缘(L2 Loss基于高斯先验,L1 Loss基于拉普拉斯先验)。 - -GAN Loss为LSGAN的最小二乘Loss,并使用PatchGAN(进一步保证生成图像的清晰度)。PatchGAN将图像换分成很多个Patch,并对每一个Patch使用判别器进行判别(实际代码实现有更取巧的办法),将所有Patch的Loss求平均作为最终的Loss。 - - - -# 7.2.2 pix2pixHD:高分辨率图像生成 -这篇paper作为pix2pix改进版本,如其名字一样,主要是可以产生高分辨率的图像。具体来说,作者的贡献主要在以下两个方面: -- 使用多尺度的生成器以及判别器等方式从而生成高分辨率图像。 -- 使用了一种非常巧妙的方式,实现了对于同一个输入,产生不同的输出。并且实现了交互式的语义编辑方式 -## 如何生成高分辨率图像 -为了生成高分辨率图像,作者主要从三个层面做了改进: -- 模型结构 -- Loss设计 -- 使用Instance-map的图像进行训练。 -### 模型结构 -![pix2pixHD生成器结构](./img/ch7/pix2pixHD网络结构.png) -生成器由两部分组成,G1和G2,其中G2又被割裂成两个部分。G1和pix2pix的生成器没有差别,就是一个end2end的U-Net结构。G2的左半部分提取特征,并和G1的输出层的前一层特征进行相加融合信息,把融合后的信息送入G2的后半部分输出高分辨率图像。 - -判别器使用多尺度判别器,在三个不同的尺度上进行判别并对结果取平均。判别的三个尺度为:原图,原图的1/2降采样,原图的1/4降采样。显然,越粗糙的尺度感受野越大,越关注全局一致性。 - -生成器和判别器均使用多尺度结构实现高分辨率重建,思路和PGGAN类似,但实际做法差别比较大。 - -### Loss设计 -这里的Loss由三部分组成: -- GAN loss:和pix2pix一样,使用PatchGAN。 -- Feature matching loss:将生成的样本和Ground truth分别送入判别器提取特征,然后对特征做Element-wise loss -- Content loss:将生成的样本和Ground truth分别送入VGG16提取特征,然后对特征做Element-wise loss -![pix2pixHD Loss](./img/ch7/pix2pixHD_Loss.png) - -使用Feature matching loss和Content loss计算特征的loss,而不是计算生成样本和Ground truth的MSE,主要在于MSE会造成生成的图像过度平滑,缺乏细节。Feature matching loss和Content loss只保证内容一致,细节则由GAN去学习。 -### 使用Instance-map的图像进行训练 -pix2pix采用语义分割的结果进行训练,可是语义分割结果没有对同类物体进行区分,导致多个同一类物体排列在一起的时候出现模糊,这在街景图中尤为常见。在这里,作者使用个体分割(Instance-level segmention)的结果来进行训练,因为个体分割的结果提供了同一类物体的边界信息。具体做法如下: -- 根据个体分割的结果求出Boundary map -- 将Boundary map与输入的语义标签concatnate到一起作为输入 -Boundary map求法很简单,直接遍历每一个像素,判断其4邻域像素所属语义类别信息,如果有不同,则置为1。下面是一个示例: -![Boundary map](./img/ch7/Boundary_map.png) -### 语义编辑 -不同于pix2pix实现生成多样性的方法(使用Dropout),这里采用了一个非常巧妙的办法,即学习一个条件(Condition)作为条件GAN的输入,不同的输入条件就得到了不同的输出,从而实现了多样化的输出,而且还是可编辑的。具体做法如下: -![语义编辑](./img/ch7/语义编辑.png) -- 首先训练一个编码器 -- 利用编码器提取原始图片的特征,然后根据Labels信息进行Average pooling,得到特征(上图的Features)。这个Features的每一类像素的值都代表了这类标签的信息。 -- 如果输入图像有足够的多,那么Features的每一类像素的值就代表了这类物体的先验分布。 -- 对所有输入的训练图像通过编码器提取特征,然后进行K-means聚类,得到K个聚类中心,以K个聚类中心代表不同的颜色,纹理等信息。 -- 实际生成图像时,除了输入语义标签信息,还要从K个聚类中心随机选择一个,即选择一个颜色/纹理风格 - -这个方法总的来说非常巧妙,通过学习数据的隐变量达到控制图像颜色纹理风格信息。 - -### 总结 -作者主要的贡献在于: -- 提出了生成高分辨率图像的多尺度网络结构,包括生成器,判别器 -- 提出了Feature loss和VGG loss提升图像的分辨率 -- 通过学习隐变量达到控制图像颜色,纹理风格信息 -- 通过Boundary map提升重叠物体的清晰度 - -可以看出,这篇paper除了第三点,都是针对性的解决高分辨率图像生成的问题的。可是本篇工作只是生成了高分辨率的图像,那对于视频呢?接下来会介绍Vid2Vid,这篇paper站在pix2pixHD的基础上,继续做了许多拓展,特别是针对视频前后帧不一致的问题做了许多优化。 - - -# 7.2.3 vid2vid:高分辨率视频生成 -待续。。。。 - - -## 7.1 GAN的「生成」的本质是什么? -GAN的形式是:两个网络,G(Generator)和D(Discriminator)。Generator是一个生成图片的网络,它接收一个随机的噪声z,记做G(z)。Discriminator是一个判别网络,判别一张图片是不是“真实的”。它的输入是x,x代表一张图片,输出D(x)代表x为真实图片的概率,如果为1,就代表100%是真实的图片,而输出为0,就代表不可能是真实的图片。 - -GAN*生成*能力是*学习分布*,引入的latent variable的noise使习得的概率分布进行偏移。因此在训练GAN的时候,latent variable**不能**引入均匀分布(uniform distribution),因为均匀分布的数据的引入并不会改变概率分布。 - -## 7.2 GAN能做数据增广吗? -GAN能够从一个模型引入一个随机数之后「生成」无限的output,用GAN来做数据增广似乎很有吸引力并且是一个极清晰的一个insight。然而,纵观整个GAN的训练过程,Generator习得分布再引入一个Distribution(Gaussian或其他)的噪声以「骗过」Discriminator,并且无论是KL Divergence或是Wasserstein Divergence,本质还是信息衡量的手段(在本章中其余部分介绍),能「骗过」Discriminator的Generator一定是能在引入一个Distribution的噪声的情况下最好的结合已有信息。 - -训练好的GAN应该能够很好的使用已有的数据的信息(特征或分布),现在问题来了,这些信息本来就包含在数据里面,有必要把信息丢到Generator学习使得的结果加上噪声作为训练模型的输入吗? - -## 7.3 VAE与GAN有什么不同? -1. VAE可以直接用在离散型数据。 -2. VAE整个训练流程只靠一个假设的loss函数和KL Divergence逼近真实分布。GAN没有假设单个loss函数, 而是让判别器D和生成器G互相博弈,以期得到Nash Equilibrium。 - -## 7.4 有哪些优秀的GAN? - -### 7.4.1 DCGAN - -[DCGAN](http://arxiv.org/abs/1511.06434)是GAN较为早期的「生成」效果最好的GAN了,很多人用DCGAN的简单、有效的生成能力做了很多很皮的工作,比如[GAN生成二次元萌妹](https://blog.csdn.net/liuxiao214/article/details/74502975)之类。 -关于DCGAN主要集中讨论以下问题: - -1. DCGAN的contribution? -2. DCGAN实操上有什么问题? - -效果好个人主要认为是引入了卷积并且给了一个非常优雅的结构,DCGAN的Generator和Discriminator几乎是**对称的**,而之后很多研究都遵从了这个对称结构,如此看来学界对这种对称架构有极大的肯定。完全使用了卷积层代替全链接层,没有pooling和upsample。其中upsample是将low resolution到high resolution的方法,而DCGAN用卷积的逆运算来完成low resolution到high resolution的操作,这简单的替换为什么成为提升GAN稳定性的原因? -![Upsample原理](./img/ch7/upsample.png) - -图中是Upsample的原理图,十分的直观,宛如低分屏换高分屏。然而Upsample和逆卷积最大的不一样是Upsample其实只能放一样的颜色来填充,而逆卷积它是个求值的过程,也就是它要算出一个具体值来,可能是一样的也可能是不一样的——如此,孰优孰劣高下立判。 - -DCGAN提出了其生成的特征具有向量的计算特性。 - -[DCGAN Keras实现](https://github.com/jacobgil/keras-dcgan) -### 7.4.2 WGAN/WGAN-GP - -WGAN及其延伸是被讨论的最多的部分,原文连发两文,第一篇(Towards principled methods for training generative adversarial networks)非常solid的提了一堆的数学,一作Arjovsky克朗所的数学能力果然一个打十几个。后来给了第二篇Wasserstein GAN,可以说直接给结果了,和第一篇相比,第二篇更加好接受。 - -然而Wasserstein Divergence真正牛逼的地方在于,几乎对所有的GAN,Wasserstein Divergence可以直接秒掉KL Divergence。那么这个时候就有个问题呼之欲出了: - -**KL/JS Divergence为什么不好用?Wasserstein Divergence牛逼在哪里?** - -**KL Divergence**是两个概率分布P和Q差别的**非对称性**的度量。KL Divergence是用来度量使用基于Q的编码来编码来自P的样本平均所需的额外的位元数(即分布的平移量)。 而**JS Divergence**是KL Divergence的升级版,解决的是**对称性**的问题。即:JS Divergence是对称的。并且由于KL Divergence不具有很好的对称性,将KL Divergence考虑成距离可能是站不住脚的,并且可以由KL Divergence的公式中看出来,平移量$\to 0$的时候,KL Divergence直接炸了。 - -KL Divergence: -$$D_{KL}(P||Q)=-\sum_{x\in X}P(x) log\frac{1}{P(x)}+\sum_{x\in X}p(x)log\frac{1}{Q(x)}=\sum_{x\in X}p(x)log\frac{P(x)}{Q(x)}$$ - -JS Divergence: - -$$JS(P_1||P_2)=\frac{1}{2}KL(P_1||\frac{P_1+P_2}{2})$$ - -**Wasserstein Divergence**:如果两个分配P,Q离得很远,完全没有重叠的时候,KL Divergence毫无意义,而此时JS Divergence值是一个常数。这使得在这个时候,梯度直接消失了。 - -**WGAN从结果上看,对GAN的改进有哪些?** - -1. 判别器最后一层去掉sigmoid -2. 生成器和判别器的loss不取log -3. 对更新后的权重强制截断到一定范围内,比如[-0.01,0.01],以满足lipschitz连续性条件。 -4. 论文中也推荐使用SGD,RMSprop等优化器,不要基于使用动量的优化算法,比如adam。 - -然而,由于D和G其实是各自有一个loss的,G和D是可以**用不同的优化器**的。个人认为Best Practice是G用SGD或RMSprop,而D用Adam。 - -很期待未来有专门针对寻找均衡态的优化方法。 - -**WGAN-GP的改进有哪些?** - -**如何理解Wasserstein距离?** -Wasserstein距离与optimal transport有一些关系,并且从数学上想很好的理解需要一定的测度论的知识。 - -### 7.4.3 condition GAN -条件生成对抗网络(CGAN, Conditional Generative Adversarial Networks)作为一个GAN的改进,其一定程度上解决了GAN生成结果的不确定性。如果在Mnist数据集上训练原始GAN,GAN生成的图像是完全不确定的,具体生成的是数字1,还是2,还是几,根本不可控。为了让生成的数字可控,我们可以把数据集做一个切分,把数字0~9的数据集分别拆分开训练9个模型,不过这样太麻烦了,也不现实。因为数据集拆分不仅仅是分类麻烦,更主要在于,每一个类别的样本少,拿去训练GAN很有可能导致欠拟合。因此,CGAN就应运而生了。我们先看一下CGAN的网络结构: -![CGAN网络结构](./img/ch7/CGAN网络结构.png) -从网络结构图可以看到,对于生成器Generator,其输入不仅仅是随机噪声的采样z,还有欲生成图像的标签信息。比如对于mnist数据生成,就是一个one-hot向量,某一维度为1则表示生成某个数字的图片。同样地,判别器的输入也包括样本的标签。这样就使得判别器和生成器可以学习到样本和标签之间的联系。Loss如下: -$$\mathop {\min }\limits_G \mathop {\max }\limits_D V(D,G) = {{\rm E}_{x\sim{p_{data}}(x)}}[\log D(x|y)] + {{\rm E}_{z\sim{p_z}(z)}}[\log (1 - D(G(z|y)))]$$ -Loss设计和原始GAN基本一致,只不过生成器,判别器的输入数据是一个条件分布。在具体编程实现时只需要对随机噪声采样z和输入条件y做一个级联即可。 -### 7.4.4 InfoGAN -通过最大化互信息(c,c’)来生成同类别的样本。 - -$$L^{infoGAN}_{D,Q}=L^{GAN}_D-\lambda L_1(c,c')$$ -$$L^{infoGAN}_{G}=L^{GAN}_G-\lambda L_1(c,c')$$ - -### 7.4.5 CycleGAN - -**CycleGAN与DualGAN之间的区别** - -### 7.4.6 StarGAN -目前Image-to-Image Translation做的最好的GAN。 - -## 7.5 GAN训练有什么难点? -由于GAN的收敛要求**两个网络(D&G)同时达到一个均衡** - -## 7.6 GAN与强化学习中的AC网络有何区别? -强化学习中的AC网络也是Dual Network,似乎从某个角度上理解可以为一个GAN。但是GAN本身 - -## 7.7 GAN的可创新的点 -GAN是一种半监督学习模型,对训练集不需要太多有标签的数据。我认为GAN用在Super Resolution、Inpainting、Image-to-Image Translation(俗称鬼畜变脸)也好,无非是以下三点: - -1. 更高效的无监督的利用卷积结构或者结合网络结构的特点对特征进行**复用**。(如Image-to-Image Translation提取特征之后用loss量化特征及其share的信息以完成整个特征复用过程) -2. 一个高效的loss function来**量化变化**。 -3. 一个短平快的拟合分布的方法。(如WGAN对GAN的贡献等) - -当然还有一些非主流的方案,比如说研究latent space甚至如何优雅的加噪声,这类方案虽然很重要,但是囿于本人想象力及实力不足,难以想到解决方案。 - -## 7.8 如何训练GAN? -判别器D在GAN训练中是比生成器G更强的网络 - -Instance Norm比Batch Norm的效果要更好。 - -使用逆卷积来生成图片会比用全连接层效果好,全连接层会有较多的噪点,逆卷积层效果清晰。 - -## 7.9 GAN如何解决NLP问题 - -GAN只适用于连续型数据的生成,对于离散型数据效果不佳,因此假如NLP方法直接应用的是character-wise的方案,Gradient based的GAN是无法将梯度Back propagation(BP)给生成网络的,因此从训练结果上看,GAN中G的表现长期被D压着打。 -## 7.10 Reference - -### DCGAN部分: -* Radford, A., Metz, L., & Chintala, S. (2015). Unsupervised representation learning with deep convolutional generative adversarial networks. arXiv preprint arXiv:1511.06434. -* Long, J., Shelhamer, E., & Darrell, T. (2015). Fully convolutional networks for semantic segmentation. In Proceedings of the IEEE conference on computer vision and pattern recognition (pp. 3431-3440). -* [可视化卷积操作](https://github.com/vdumoulin/conv_arithmetic) -### WGAN部分: -* Arjovsky, M., Chintala, S., & Bottou, L. (2017). Wasserstein gan. arXiv preprint arXiv:1701.07875. -* Nowozin, S., Cseke, B., & Tomioka, R. (2016). f-gan: Training generative neural samplers using variational divergence minimization. In Advances in Neural Information Processing Systems (pp. 271-279). -* Wu, J., Huang, Z., Thoma, J., Acharya, D., & Van Gool, L. (2018, September). Wasserstein Divergence for GANs. In Proceedings of the European Conference on Computer Vision (ECCV) (pp. 653-668). - - -### Image2Image Translation -* Isola P, Zhu JY, Zhou T, Efros AA. Image-to-image translation with conditional adversarial networks. arXiv preprint. 2017 Jul 21. -* Zhu, J. Y., Park, T., Isola, P., & Efros, A. A. (2017). Unpaired image-to-image translation using cycle-consistent adversarial networks. arXiv preprint.(CycleGAN) -* Choi, Y., Choi, M., Kim, M., Ha, J. W., Kim, S., & Choo, J. (2017). Stargan: Unified generative adversarial networks for multi-domain image-to-image translation. arXiv preprint, 1711. -* Murez, Z., Kolouri, S., Kriegman, D., Ramamoorthi, R., & Kim, K. (2017). Image to image translation for domain adaptation. arXiv preprint arXiv:1712.00479, 13. - -### GAN的训练 -* Arjovsky, M., & Bottou, L. (2017). Towards principled methods for training generative adversarial networks. arXiv preprint arXiv:1701.04862. - - - - -# 生成模型和判别模型 -https://blog.csdn.net/u010358304/article/details/79748153 -原文:https://blog.csdn.net/u010089444/article/details/78946039 - -# 生成模型和判别模型对比 -https://blog.csdn.net/love666666shen/article/details/75522489 - - -# 直观理解GAN的博弈过程 -https://blog.csdn.net/u010089444/article/details/78946039 - -# GAN原理 -1.GAN的原理: - -GAN的主要灵感来源于博弈论中零和博弈的思想,应用到深度学习神经网络上来说,就是通过生成网络G(Generator)和判别网络D(Discriminator)不断博弈,进而使G学习到数据的分布,如果用到图片生成上,则训练完成后,G可以从一段随机数中生成逼真的图像。G, D的主要功能是: - -● G是一个生成式的网络,它接收一个随机的噪声z(随机数),通过这个噪声生成图像 - -● D是一个判别网络,判别一张图片是不是“真实的”。它的输入参数是x,x代表一张图片,输出D(x)代表x为真实图片的概率,如果为1,就代表100%是真实的图片,而输出为0,就代表不可能是真实的图片 - -训练过程中,生成网络G的目标就是尽量生成真实的图片去欺骗判别网络D。而D的目标就是尽量辨别出G生成的假图像和真实的图像。这样,G和D构成了一个动态的“博弈过程”,最终的平衡点即纳什均衡点. ---------------------- -作者:山水之间2018 -来源:CSDN -原文:https://blog.csdn.net/Gavinmiaoc/article/details/79947877 - -# GAN的特点 -2. GAN的特点: - -● 相比较传统的模型,他存在两个不同的网络,而不是单一的网络,并且训练方式采用的是对抗训练方式 - -● GAN中G的梯度更新信息来自判别器D,而不是来自数据样本 - -# GAN优缺点? - -3. GAN 的优点: - -(以下部分摘自ian goodfellow 在Quora的问答) - -● GAN是一种生成式模型,相比较其他生成模型(玻尔兹曼机和GSNs)只用到了反向传播,而不需要复杂的马尔科夫链 - -● 相比其他所有模型, GAN可以产生更加清晰,真实的样本 - -● GAN采用的是一种无监督的学习方式训练,可以被广泛用在无监督学习和半监督学习领域 - -● 相比于变分自编码器, GANs没有引入任何决定性偏置( deterministic bias),变分方法引入决定性偏置,因为他们优化对数似然的下界,而不是似然度本身,这看起来导致了VAEs生成的实例比GANs更模糊 - -● 相比VAE, GANs没有变分下界,如果鉴别器训练良好,那么生成器可以完美的学习到训练样本的分布.换句话说,GANs是渐进一致的,但是VAE是有偏差的 - -● GAN应用到一些场景上,比如图片风格迁移,超分辨率,图像补全,去噪,避免了损失函数设计的困难,不管三七二十一,只要有一个的基准,直接上判别器,剩下的就交给对抗训练了。 - - -4. GAN的缺点: - -● 训练GAN需要达到纳什均衡,有时候可以用梯度下降法做到,有时候做不到.我们还没有找到很好的达到纳什均衡的方法,所以训练GAN相比VAE或者PixelRNN是不稳定的,但我认为在实践中它还是比训练玻尔兹曼机稳定的多 - -● GAN不适合处理离散形式的数据,比如文本 - -● GAN存在训练不稳定、梯度消失、模式崩溃的问题(目前已解决) ---------------------- -作者:山水之间2018 -来源:CSDN -原文:https://blog.csdn.net/Gavinmiaoc/article/details/79947877 -版权声明:本文为博主原创文章,转载请附上博文链接! - -# 模式崩溃(model collapse)原因 -一般出现在GAN训练不稳定的时候,具体表现为生成出来的结果非常差,但是即使加长训练时间后也无法得到很好的改善。 - -具体原因可以解释如下:GAN采用的是对抗训练的方式,G的梯度更新来自D,所以G生成的好不好,得看D怎么说。具体就是G生成一个样本,交给D去评判,D会输出生成的假样本是真样本的概率(0-1),相当于告诉G生成的样本有多大的真实性,G就会根据这个反馈不断改善自己,提高D输出的概率值。但是如果某一次G生成的样本可能并不是很真实,但是D给出了正确的评价,或者是G生成的结果中一些特征得到了D的认可,这时候G就会认为我输出的正确的,那么接下来我就这样输出肯定D还会给出比较高的评价,实际上G生成的并不怎么样,但是他们两个就这样自我欺骗下去了,导致最终生成结果缺失一些信息,特征不全。 ---------------------- -作者:山水之间2018 -来源:CSDN -原文:https://blog.csdn.net/Gavinmiaoc/article/details/79947877 -版权声明:本文为博主原创文章,转载请附上博文链接! - -# 为什么GAN不适合处理文本数据 -1. 文本数据相比较图片数据来说是离散的,因为对于文本来说,通常需要将一个词映射为一个高维的向量,最终预测的输出是一个one-hot向量,假设softmax的输出是(0.2, 0.3, 0.1,0.2,0.15,0.05)那么变为onehot是(0,1,0,0,0,0),如果softmax输出是(0.2, 0.25, 0.2, 0.1,0.15,0.1 ),one-hot仍然是(0, 1, 0, 0, 0, 0),所以对于生成器来说,G输出了不同的结果但是D给出了同样的判别结果,并不能将梯度更新信息很好的传递到G中去,所以D最终输出的判别没有意义。 - -2. 另外就是GAN的损失函数是JS散度,JS散度不适合衡量不想交分布之间的距离。 - -(WGAN虽然使用wassertein距离代替了JS散度,但是在生成文本上能力还是有限,GAN在生成文本上的应用有seq-GAN,和强化学习结合的产物) ---------------------- -作者:山水之间2018 -来源:CSDN -原文:https://blog.csdn.net/Gavinmiaoc/article/details/79947877 -版权声明:本文为博主原创文章,转载请附上博文链接! - -# 训练GAN的一些技巧 - -1. 输入规范化到(-1,1)之间,最后一层的激活函数使用tanh(BEGAN除外) - -2. 使用wassertein GAN的损失函数, - -3. 如果有标签数据的话,尽量使用标签,也有人提出使用反转标签效果很好,另外使用标签平滑,单边标签平滑或者双边标签平滑 - -4. 使用mini-batch norm, 如果不用batch norm 可以使用instance norm 或者weight norm - -5. 避免使用RELU和pooling层,减少稀疏梯度的可能性,可以使用leakrelu激活函数 - -6. 优化器尽量选择ADAM,学习率不要设置太大,初始1e-4可以参考,另外可以随着训练进行不断缩小学习率, - -7. 给D的网络层增加高斯噪声,相当于是一种正则 ---------------------- -作者:山水之间2018 -来源:CSDN -原文:https://blog.csdn.net/Gavinmiaoc/article/details/79947877 -版权声明:本文为博主原创文章,转载请附上博文链接! - - - -# 实例理解GAN实现过程 -https://blog.csdn.net/sxf1061926959/article/details/54630462 - -# DCGAN、WGAN、WGAN-GP、LSGAN、BEGAN原理总结及对比 -https://blog.csdn.net/qq_25737169/article/details/78857788 - -## DCGAN -### DCGAN原理理解? -### 优缺点? - -# GAN对噪声z的分布有要求吗?常用哪些分布? -一般没有特别要求,常用有高斯分布、均匀分布。噪声的维数至少要达到数据流形的内在维数,才能产生足够的diversity,mnist大概是6维,CelebA大概是20维(参考:https://zhuanlan.zhihu.com/p/26528060) -https://blog.csdn.net/witnessai1/article/details/78507065/ - -# 现有GAN存在哪些关键属性缺失? -http://www.elecfans.com/d/707141.html -# 图解什么是GAN -https://www.cnblogs.com/Darwin2000/p/6984253.html - -# GAN有哪些训练难点\原因及解决方案 -https://www.sohu.com/a/143961544_741733 - -# 近年GAN有哪些突破口? -https://baijiahao.baidu.com/s?id=1593092872607620265&wfr=spider&for=pc diff --git "a/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/68747470733a2f2f6c656f6e6172646f617261756a6f73616e746f732e676974626f6f6b732e696f2f6172746966696369616c2d696e74656c6967656e63652f636f6e74.png" "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/68747470733a2f2f6c656f6e6172646f617261756a6f73616e746f732e676974626f6f6b732e696f2f6172746966696369616c2d696e74656c6967656e63652f636f6e74.png" deleted file mode 100644 index 71a43bb5..00000000 Binary files "a/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/68747470733a2f2f6c656f6e6172646f617261756a6f73616e746f732e676974626f6f6b732e696f2f6172746966696369616c2d696e74656c6967656e63652f636f6e74.png" and /dev/null differ diff --git "a/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/68747470733a2f2f6e6f74652e796f7564616f2e636f6d2f7977732f7075626c69632f7265736f757263652f636539303432353631643535333464386635373936303137.png" "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/68747470733a2f2f6e6f74652e796f7564616f2e636f6d2f7977732f7075626c69632f7265736f757263652f636539303432353631643535333464386635373936303137.png" deleted file mode 100644 index a25a804c..00000000 Binary files "a/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/68747470733a2f2f6e6f74652e796f7564616f2e636f6d2f7977732f7075626c69632f7265736f757263652f636539303432353631643535333464386635373936303137.png" and /dev/null differ diff --git "a/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/DSSD-01.png" "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/DSSD-01.png" new file mode 100644 index 00000000..dc5af485 Binary files /dev/null and "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/DSSD-01.png" differ diff --git "a/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/DSSD-02.png" "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/DSSD-02.png" new file mode 100644 index 00000000..ca2622bf Binary files /dev/null and "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/DSSD-02.png" differ diff --git "a/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/DSSD-03.png" "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/DSSD-03.png" new file mode 100644 index 00000000..b2b0f41c Binary files /dev/null and "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/DSSD-03.png" differ diff --git "a/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/FPN-01.png" "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/FPN-01.png" new file mode 100644 index 00000000..5b16fef9 Binary files /dev/null and "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/FPN-01.png" differ diff --git "a/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/FPN-02.png" "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/FPN-02.png" new file mode 100644 index 00000000..8de57618 Binary files /dev/null and "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/FPN-02.png" differ diff --git "a/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/FPN-03.png" "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/FPN-03.png" new file mode 100644 index 00000000..862b5c7b Binary files /dev/null and "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/FPN-03.png" differ diff --git "a/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/FPN-04.png" "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/FPN-04.png" new file mode 100644 index 00000000..ccdd8556 Binary files /dev/null and "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/FPN-04.png" differ diff --git "a/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/M2Det-01.png" "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/M2Det-01.png" new file mode 100644 index 00000000..c8ac8a86 Binary files /dev/null and "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/M2Det-01.png" differ diff --git "a/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/M2Det-02.png" "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/M2Det-02.png" new file mode 100644 index 00000000..cd5b582d Binary files /dev/null and "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/M2Det-02.png" differ diff --git "a/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/M2Det-03.png" "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/M2Det-03.png" new file mode 100644 index 00000000..ed41990c Binary files /dev/null and "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/M2Det-03.png" differ diff --git "a/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/Mask R-CNN-01.png" "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/Mask R-CNN-01.png" new file mode 100644 index 00000000..d3eb5e6d Binary files /dev/null and "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/Mask R-CNN-01.png" differ diff --git "a/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/Mask R-CNN-02.png" "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/Mask R-CNN-02.png" new file mode 100644 index 00000000..69ae2426 Binary files /dev/null and "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/Mask R-CNN-02.png" differ diff --git "a/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/Mask R-CNN-03.png" "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/Mask R-CNN-03.png" new file mode 100644 index 00000000..e1de2caf Binary files /dev/null and "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/Mask R-CNN-03.png" differ diff --git "a/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/Mask R-CNN-04.png" "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/Mask R-CNN-04.png" new file mode 100644 index 00000000..397b29b5 Binary files /dev/null and "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/Mask R-CNN-04.png" differ diff --git "a/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/RFBNet-01.png" "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/RFBNet-01.png" new file mode 100644 index 00000000..dda9a6cf Binary files /dev/null and "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/RFBNet-01.png" differ diff --git "a/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/RFBNet-02.png" "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/RFBNet-02.png" new file mode 100644 index 00000000..d8566591 Binary files /dev/null and "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/RFBNet-02.png" differ diff --git "a/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/RFBNet-03.png" "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/RFBNet-03.png" new file mode 100644 index 00000000..f09c6379 Binary files /dev/null and "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/img/ch8/RFBNet-03.png" differ diff --git "a/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/modify_log.txt" "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/modify_log.txt" index 0eed1d29..386b09e2 100644 --- "a/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/modify_log.txt" +++ "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/modify_log.txt" @@ -26,4 +26,21 @@ modify_log---->用来记录修改日志 5. 新增所有论文链接 <----lp-2018-11-18----> -1.修改SSD和YOLO系列 \ No newline at end of file +1. 修改SSD和YOLO系列 + +<----cfj-2018-12-09----> +1. 新增8.1.4目标检测有哪些应用? +2. 新增8.2节Two-Stage检测算法:FPN、Mask R-CNN +3. 删除8.2节Two-Stage检测算法:RefineDet和Cascade R-CNN +4. 新增8.3节One-Stage检测算法:DSSD和RFBNet +5. 删除8.3节One-Stage检测算法:FSSD +5. 修改8.4人脸检测章节序号 +6. 新增8.5节目标检测的技巧汇总 +7. 新增8.6节目标检测的常用数据集 + +<----cfj-2019-12-21----> +1. 新增SSD系列创新点 +2. 新增YOLO系列创新点 + +<----cfj-2019-01-05----> +1. 新增8.3节One-Stage检测算法:M2Det diff --git "a/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/\347\254\254\345\205\253\347\253\240_\347\233\256\346\240\207\346\243\200\346\265\213.md" "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/\347\254\254\345\205\253\347\253\240_\347\233\256\346\240\207\346\243\200\346\265\213.md" index 9fcfa806..8fa31e33 100644 --- "a/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/\347\254\254\345\205\253\347\253\240_\347\233\256\346\240\207\346\243\200\346\265\213.md" +++ "b/ch08_\347\233\256\346\240\207\346\243\200\346\265\213/\347\254\254\345\205\253\347\253\240_\347\233\256\346\240\207\346\243\200\346\265\213.md" @@ -2,6 +2,12 @@ **更新日志:** +2019.01.05(陈方杰):新增8.3节One-Stage检测算法:M2Det + +2018.12.21(陈方杰):新增SSD系列创新点,新增YOLO系列创新点 + +2018.12.09(陈方杰):新增目标检测有哪些应用,新增FPN、Mask R-CNN、DSSD和RFBNet算法,新增目标检测Tricks,新增目标检测的常用数据集,删除RefineDet、Cascade R-CNN和FSSD,修改人脸检测章节序号 + 2018.11.18(陈方杰):修改第八章目标检测目录,新增目标检测基本概念,修改R-CNN、Fast R-CNN、RetinaNet,新增待完善论文FPN、RefineDet、RFBNet,以及新增所有论文链接。 2018.11.18(刘鹏):新增人脸检测部分,修改ssd-yolo系列 @@ -22,9 +28,11 @@ 8.1.1 什么是目标检测? -8.1.2 目标检测要解决的核心问题 +8.1.2 目标检测要解决的核心问题? + +8.1.3 目标检测算法分类? -8.1.2 目标检测算法 +8.1.4 目标检测有哪些应用? 8.2 Two Stage目标检测算法 @@ -40,31 +48,55 @@ 8.2.6 Mask R-CNN -8.2.7 RefineDet - -8.2.8 Cascade R-CNN - 8.3 One Stage目标检测算法 8.3.1 SSD 8.3.2 DSSD -8.3.3 FSSD +8.3.3 YOLOv1 + +8.3.4 YOLOv2 + +8.3.5 YOLO9000 + +8.3.6 YOLOv3 + +8.3.7 RetinaNet + +8.3.8 RFBNet + +8.3.9 M2Det + +8.4 人脸检测 + +8.4.1 目前主要有人脸检测方法分类? + +8.4.2 如何检测图片中不同大小的人脸? -8.3.4 YOLOv1 +8.4.3 如何设定算法检测最小人脸尺寸? -8.3.5 YOLOv2 +8.4.4 如何定位人脸的位置? -8.3.6 YOLO9000 +8.4.5 如何通过一个人脸的多个框确定最终人脸框位置? -8.3.7 YOLOv3 +8.4.6 基于级联卷积神经网络的人脸检测(Cascade CNN) -8.3.8 RetinaNet +8.4.7 基于多任务卷积神经网络的人脸检测(MTCNN) -8.3.9 RFBNet +8.4.8 Facebox -8.3.10 M2Det +8.5 目标检测的技巧汇总 + +8.6 目标检测的常用数据集 + +8.6.1 PASCAL VOC + +8.6.2 MS COCO + +8.6.3 Google Open Image + +8.6.4 ImageNet Reference @@ -74,7 +106,7 @@ Reference ### 8.1.1 什么是目标检测? -目标检测(Object Detection)的任务是找出图像中所有感兴趣的目标(物体),确定它们的类别和位置,是计算机视觉领域的核心问题之一。由于各类物体有不同的外观,形状,姿态,加上成像时光照,遮挡等因素的干扰,目标检测一直是计算机视觉领域最具有挑战性的问题。 +目标检测(Object Detection)的任务是找出图像中所有感兴趣的目标(物体),确定它们的类别和位置,是计算机视觉领域的核心问题之一。由于各类物体有不同的外观、形状和姿态,加上成像时光照、遮挡等因素的干扰,目标检测一直是计算机视觉领域最具有挑战性的问题。 计算机视觉中关于图像识别有四大类任务: @@ -98,9 +130,7 @@ Reference 3.目标可能有各种不同的形状。 -如果用矩形框来定义目标,则矩形有不同的宽高比。由于目标的宽高比不同,因此采用经典的滑动窗口+图像缩放的方案解决通用目标检测问题的成本太高。 - -### 8.1.2 目标检测算法分类? +### 8.1.3 目标检测算法分类? 基于深度学习的目标检测算法主要分为两类: @@ -122,6 +152,10 @@ Reference ![](./img/ch8/8.1.2.png) +### 8.1.4 目标检测有哪些应用? + +目标检测具有巨大的实用价值和应用前景。应用领域包括人脸检测、行人检测、车辆检测、飞机航拍或卫星图像中道路的检测、车载摄像机图像中的障碍物检测、医学影像在的病灶检测等。还有在安防领域中,可以实现比如安全帽、安全带等动态检测,移动侦测、区域入侵检测、物品看护等功能。 + ## 8.2 Two Stage目标检测算法 ### 8.2.1 R-CNN @@ -137,10 +171,10 @@ Reference - arXiv:http://arxiv.org/abs/1311.2524 - github(caffe):https://github.com/rbgirshick/rcnn -**R-CNN 创新点** +**R-CNN有哪些创新点?** -- 使用CNN(ConvNet)对 region proposals 计算 feature vectors。从经验驱动特征(SIFT、HOG)到数据驱动特征(CNN feature map),提高特征对样本的表示能力。 -- 采用大样本下(ILSVRC)有监督预训练和小样本(PASCAL)微调(fine-tuning)的方法解决小样本难以训练甚至过拟合等问题。 +1. 使用CNN(ConvNet)对 region proposals 计算 feature vectors。从经验驱动特征(SIFT、HOG)到数据驱动特征(CNN feature map),提高特征对样本的表示能力。 +2. 采用大样本下(ILSVRC)有监督预训练和小样本(PASCAL)微调(fine-tuning)的方法解决小样本难以训练甚至过拟合等问题。 注:ILSVRC其实就是众所周知的ImageNet的挑战赛,数据量极大;PASCAL数据集(包含目标检测和图像分割等),相对较小。 @@ -190,7 +224,7 @@ R-CNN在VOC 2007测试集上mAP达到58.5%,打败当时所有的目标检测 - arXiv:https://arxiv.org/abs/1504.08083 - github(Official):https://github.com/rbgirshick/fast-rcnn -**Fast R-CNN 创新点** +**Fast R-CNN有哪些创新点?** 1. 只对整幅图像进行一次特征提取,避免R-CNN中的冗余特征提取 2. 用RoI pooling层替换最后一层的max pooling层,同时引入建议框数据,提取相应建议框特征 @@ -268,37 +302,39 @@ RoI是Region of Interest的简写,一般是指图像上的区域框,但这 - github(official, Matlab):https://github.com/ShaoqingRen/faster_rcnn - github(official, Caffe):https://github.com/rbgirshick/py-faster-rcnn - Fast R-CNN依赖于外部候选区域方法,如选择性搜索。但这些算法在CPU上运行且速度很慢。在测试中,Fast R-CNN需要2.3秒来进行预测,其中2秒用于生成2000个ROI。Faster R-CNN采用与Fast R-CNN相同的设计,只是它用内部深层网络代替了候选区域方法。新的候选区域网络(RPN)在生成ROI时效率更高,并且以每幅图像10毫秒的速度运行。 - ![](./img/ch8/8.1.13.png) +**Fast R-CNN有哪些创新点?** + +Fast R-CNN依赖于外部候选区域方法,如选择性搜索。但这些算法在CPU上运行且速度很慢。在测试中,Fast R-CNN需要2.3秒来进行预测,其中2秒用于生成2000个ROI。Faster R-CNN采用与Fast R-CNN相同的设计,只是它用内部深层网络代替了候选区域方法。新的候选区域网络(RPN)在生成ROI时效率更高,并且以每幅图像10毫秒的速度运行。 +![](./img/ch8/8.1.13.png) - 图8.1.13 Faster R-CNN的流程图 - Faster R-CNN的流程图与Fast R-CNN相同,采用外部候选区域方法代替了内部深层网络。 - ![](./img/ch8/8.1.14.png) +图8.1.13 Faster R-CNN的流程图 +Faster R-CNN的流程图与Fast R-CNN相同,采用外部候选区域方法代替了内部深层网络。 +![](./img/ch8/8.1.14.png) - 图8.1.14 - **候选区域网络** +图8.1.14 +**候选区域网络** - 候选区域网络(RPN)将第一个卷积网络的输出特征图作为输入。它在特征图上滑动一个3×3的卷积核,以使用卷积网络(如下所示的ZF网络)构建与类别无关的候选区域。其他深度网络(如VGG或ResNet)可用于更全面的特征提取,但这需要以速度为代价。ZF网络最后会输出256个值,它们将馈送到两个独立的全连接层,以预测边界框和两个objectness分数,这两个objectness分数度量了边界框是否包含目标。我们其实可以使用回归器计算单个objectness分数,但为简洁起见,Faster R-CNN使用只有两个类别的分类器:即带有目标的类别和不带有目标的类别。 - ![](./img/ch8/8.1.15.png) +候选区域网络(RPN)将第一个卷积网络的输出特征图作为输入。它在特征图上滑动一个3×3的卷积核,以使用卷积网络(如下所示的ZF网络)构建与类别无关的候选区域。其他深度网络(如VGG或ResNet)可用于更全面的特征提取,但这需要以速度为代价。ZF网络最后会输出256个值,它们将馈送到两个独立的全连接层,以预测边界框和两个objectness分数,这两个objectness分数度量了边界框是否包含目标。我们其实可以使用回归器计算单个objectness分数,但为简洁起见,Faster R-CNN使用只有两个类别的分类器:即带有目标的类别和不带有目标的类别。 +![](./img/ch8/8.1.15.png) - 图8.1.15 - 对于特征图中的每一个位置,RPN会做k次预测。因此,RPN将输出4×k个坐标和每个位置上2×k个得分。下图展示了8×8的特征图,且有一个3×3的卷积核执行运算,它最后输出8×8×3个ROI(其中k=3)。下图(右)展示了单个位置的3个候选区域。 - ![](./img/ch8/8.1.16.png) +图8.1.15 +对于特征图中的每一个位置,RPN会做k次预测。因此,RPN将输出4×k个坐标和每个位置上2×k个得分。下图展示了8×8的特征图,且有一个3×3的卷积核执行运算,它最后输出8×8×3个ROI(其中k=3)。下图(右)展示了单个位置的3个候选区域。 +![](./img/ch8/8.1.16.png) - 图8.1.16 - 假设最好涵盖不同的形状和大小。因此,Faster R-CNN不会创建随机边界框。相反,它会预测一些与左上角名为锚点的参考框相关的偏移量(如x, y)。我们限制这些偏移量的值,因此我们的猜想仍然类似于锚点。 - ![](./img/ch8/8.1.17.png) +图8.1.16 +假设最好涵盖不同的形状和大小。因此,Faster R-CNN不会创建随机边界框。相反,它会预测一些与左上角名为锚点的参考框相关的偏移量(如x, y)。我们限制这些偏移量的值,因此我们的猜想仍然类似于锚点。 +![](./img/ch8/8.1.17.png) - 图8.1.17 - 要对每个位置进行k个预测,我们需要以每个位置为中心的k个锚点。每个预测与特定锚点相关联,但不同位置共享相同形状的锚点。 - ![](./img/ch8/8.1.18.png) +图8.1.17 +要对每个位置进行k个预测,我们需要以每个位置为中心的k个锚点。每个预测与特定锚点相关联,但不同位置共享相同形状的锚点。 +![](./img/ch8/8.1.18.png) - 图8.1.18 - 这些锚点是精心挑选的,因此它们是多样的,且覆盖具有不同比例和宽高比的现实目标。这使得我们可以用更好的猜想来指导初始训练,并允许每个预测专门用于特定的形状。该策略使早期训练更加稳定和简便。 - ![](./img/ch8/8.1.19.png) +图8.1.18 +这些锚点是精心挑选的,因此它们是多样的,且覆盖具有不同比例和宽高比的现实目标。这使得我们可以用更好的猜想来指导初始训练,并允许每个预测专门用于特定的形状。该策略使早期训练更加稳定和简便。 +![](./img/ch8/8.1.19.png) - 图8.1.19 - Faster R-CNN使用更多的锚点。它部署9个锚点框:3个不同宽高比的3个不同大小的锚点框。每一个位置使用9个锚点,每个位置会生成2×9个objectness分数和4×9个坐标。 +图8.1.19 +Faster R-CNN使用更多的锚点。它部署9个锚点框:3个不同宽高比的3个不同大小的锚点框。每一个位置使用9个锚点,每个位置会生成2×9个objectness分数和4×9个坐标。 ### 8.2.4 R-FCN @@ -313,12 +349,12 @@ RoI是Region of Interest的简写,一般是指图像上的区域框,但这 - arXiv:https://arxiv.org/abs/1605.06409 - github(Official):https://github.com/daijifeng001/r-fcn -**R-FCN 创新点** +**R-FCN有哪些创新点?** R-FCN 仍属于two-stage 目标检测算法:RPN+R-FCN -- Fully convolutional -- 位置敏感得分图(position-sentive score maps) +1. Fully convolutional +2. 位置敏感得分图(position-sentive score maps) > our region-based detector is **fully convolutional** with almost all computation shared on the entire image. To achieve this goal, we propose **position-sensitive score maps** to address a dilemma between translation-invariance in image classification and translation-variance in object detection. @@ -368,7 +404,67 @@ ResNet-101+R-FCN:83.6% in PASCAL VOC 2007 test datasets - arXiv:https://arxiv.org/abs/1612.03144 -- [ ] TODO +**FPN有哪些创新点?** + +1. 多层特征 +2. 特征融合 + +解决目标检测中的多尺度问题,通过简单的网络连接改变,在基本不增加原有模型计算量的情况下,大幅度提升小物体(small object)检测的性能。 + +在物体检测里面,有限计算量情况下,网络的深度(对应到感受野)与 stride 通常是一对矛盾的东西,常用的网络结构对应的 stride 一般会比较大(如 32),而图像中的小物体甚至会小于 stride 的大小,造成的结果就是小物体的检测性能急剧下降。传统解决这个问题的思路包括: + +1. 图像金字塔(image pyramid),即多尺度训练和测试。但该方法计算量大,耗时较久。 +2. 特征分层,即每层分别预测对应的scale分辨率的检测结果,如SSD算法。该方法强行让不同层学习同样的语义信息,但实际上不同深度对应于不同层次的语义特征,浅层网络分辨率高,学到更多是细节特征,深层网络分辨率低,学到更多是语义特征。 + +因而,目前多尺度的物体检测主要面临的挑战为: + +1. 如何学习具有强语义信息的多尺度特征表示? +2. 如何设计通用的特征表示来解决物体检测中的多个子问题?如 object proposal, box localization, instance segmentation. +3. 如何高效计算多尺度的特征表示? + +FPN网络直接在Faster R-CNN单网络上做修改,每个分辨率的 feature map 引入后一分辨率缩放两倍的 feature map 做 element-wise 相加的操作。通过这样的连接,每一层预测所用的 feature map 都融合了不同分辨率、不同语义强度的特征,融合的不同分辨率的 feature map 分别做对应分辨率大小的物体检测。这样保证了每一层都有合适的分辨率以及强语义(rich semantic)特征。同时,由于此方法只是在原网络基础上加上了额外的跨层连接,在实际应用中几乎不增加额外的时间和计算量。作者接下来实验了将 FPN 应用在 Faster RCNN 上的性能,在 COCO 上达到了 state-of-the-art 的单模型精度。在RPN上,FPN增加了8.0个点的平均召回率(average recall。AR);在后面目标检测上,对于COCO数据集,FPN增加了2.3个点的平均精确率(average precision,AP),对于VOC数据集,FPN增加了3.8个点的AP。 + + + +![](img/ch8/FPN-01.png) + +FPN算法主要由三个模块组成,分别是: + +1. Bottom-up pathway(自底向上线路) +2. Lareral connections(横向链接) +3. Top-down path(自顶向下线路) + +![](img/ch8/FPN-02.png) + +**Bottom-up pathway** + +FPN是基于Faster R-CNN进行改进,其backbone是ResNet-101,FPN主要应用在Faster R-CNN中的RPN(用于bouding box proposal generation)和Fast R-CNN(用于object detection)两个模块中。 + +其中 RPN 和 Fast RCNN 分别关注的是召回率(recall)和精确率(precision),在这里对比的指标分别为 Average Recall(AR) 和 Average Precision(AP)。 + +注:Bottom-up可以理解为自底向上,Top-down可以理解为自顶向下。这里的下是指low-level,上是指high-level,分别对应于提取的低级(浅层)特征和高级语义(高层)特征。 + +Bottom-up pathway 是卷积网络的前向传播过程。在前向传播过程中,feature map的大小可以在某些层发生改变。一些尺度(scale)因子为2,所以后一层feature map的大小是前一层feature map大小的二分之一,根据此关系进而构成了feature pyramid(hierarchy)。 + +然而还有很多层输出的feature map是一样的大小(即不进行缩放的卷积),作者将这些层归为同一 stage。对于feature pyramid,作者为每个stage定义一个pyramid level。 + +作者将每个stage的最后一层的输出作为feature map,然后不同stage进行同一操作,便构成了feature pyramid。 + +具体来说,对于ResNets-101,作者使用了每个stage的最后一个残差结构的特征激活输出。将这些残差模块输出表示为{C2, C3, C4, C5},对应于conv2,conv3,conv4和conv5的输出,并且注意它们相对于输入图像具有{4, 8, 16, 32}像素的步长。考虑到内存占用,没有将conv1包含在金字塔中。 + +![](img/ch8/FPN-03.png) + +**Top-down pathway and lateral connections** + +Top-town pathway是上采样(upsampling)过程。而later connection(横向连接)是将上采样的结果和bottom-up pathway生成的相同大小的feature map进行融合(merge)。 + +注:上采样尺度因子为2,因为为了和之前下采样卷积的尺度因子=2一样。上采样是放大,下采样是缩小。 + +具体操作如下图所示,上采样(2x up)feature map与相同大小的bottom-up feature map进行逐像素相加融合(element-wise addition),其中bottom-up feature先要经过1x1卷积层,目的是为了减少通道维度(reduce channel dimensions)。 + +注:减少通道维度是为了将bottom-up feature map的通道数量与top-down feature map的通道数量保持一致,又因为两者feature map大小一致,所以可以进行对应位置像素的叠加(element-wise addition)。 + +![](img/ch8/FPN-04.png) ### 8.2.6 Mask R-CNN @@ -385,47 +481,68 @@ ResNet-101+R-FCN:83.6% in PASCAL VOC 2007 test datasets - github(Official):https://github.com/facebookresearch/Detectron +**Mask R-CNN有哪些创新点?** +1. Backbone:ResNeXt-101+FPN +2. RoI Align替换RoI Pooling -- [ ] TODO +Mask R-CNN是一个实例分割(Instance segmentation)算法,主要是在目标检测的基础上再进行分割。Mask R-CNN算法主要是Faster R-CNN+FCN,更具体一点就是ResNeXt+RPN+RoI Align+Fast R-CNN+FCN。 -### 8.2.7 RefineDet +![](img/ch8/Mask R-CNN-01.png) -**标题:《Single-Shot Refinement Neural Network for Object Detection》** +**Mask R-CNN算法步骤** -**时间:2017** +1. 输入一幅你想处理的图片,然后进行对应的预处理操作,或者预处理后的图片; +2. 将其输入到一个预训练好的神经网络中(ResNeXt等)获得对应的feature map; +3. 对这个feature map中的每一点设定预定个的RoI,从而获得多个候选RoI; +4. 将这些候选的RoI送入RPN网络进行二值分类(前景或背景)和BB回归,过滤掉一部分候选的RoI; +5. 对这些剩下的RoI进行RoI Align操作(即先将原图和feature map的pixel对应起来,然后将feature map和固定的feature对应起来); +6. 对这些RoI进行分类(N类别分类)、BB回归和MASK生成(在每一个RoI里面进行FCN操作)。 -**出版源:CVPR 2018** +**RoI Pooling和RoI Align有哪些不同?** -**主要链接:** +ROI Align 是在Mask-RCNN中提出的一种区域特征聚集方式,很好地解决了RoI Pooling操作中两次量化造成的区域不匹配(mis-alignment)的问题。实验显示,在检测测任务中将 RoI Pooling 替换为 RoI Align 可以提升检测模型的准确性。 -- arXiv:https://arxiv.org/abs/1711.06897 -- github(Official):https://github.com/sfzhang15/RefineDet +在常见的两级检测框架(比如Fast-RCNN,Faster-RCNN,RFCN)中,RoI Pooling 的作用是根据预选框的位置坐标在特征图中将相应区域池化为固定尺寸的特征图,以便进行后续的分类和包围框回归操作。由于预选框的位置通常是由模型回归得到的,一般来讲是浮点数,而池化后的特征图要求尺寸固定。故RoI Pooling这一操作存在两次量化的过程。 +- 将候选框边界量化为整数点坐标值。 +- 将量化后的边界区域平均分割成 k x k 个单元(bin),对每一个单元的边界进行量化。 +事实上,经过上述两次量化,此时的候选框已经和最开始回归出来的位置有一定的偏差,这个偏差会影响检测或者分割的准确度。在论文里,作者把它总结为“不匹配问题(misalignment)。 -- [ ] TODO +在常见的两级检测框架(比如Fast-RCNN,Faster-RCNN,R-FCN)中,RoI Pooling 的作用是根据预选框的位置坐标在特征图中将相应区域池化为固定尺寸的特征图,以便进行后续的分类和包围框回归操作。由于预选框的位置通常是由模型回归得到的,一般来讲是浮点数,而池化后的特征图要求尺寸固定。故RoI Pooling这一操作存在两次量化的过程。 -### 8.2.8 Cascade R-CNN +- 将候选框边界量化为整数点坐标值。 +- 将量化后的边界区域平均分割成 k x k 个单元(bin),对每一个单元的边界进行量化。 -**标题:《Cascade R-CNN: Delving into High Quality Object Detection》** +事实上,经过上述两次量化,此时的候选框已经和最开始回归出来的位置有一定的偏差,这个偏差会影响检测或者分割的准确度。在论文里,作者把它总结为“不匹配问题(misalignment)。 -**时间:2017** +下面我们用直观的例子具体分析一下上述区域不匹配问题。如下图所示,这是一个Faster-RCNN检测框架。输入一张800x800的图片,图片上有一个665x665的包围框(框着一只狗)。图片经过主干网络提取特征后,特征图缩放步长(stride)为32。因此,图像和包围框的边长都是输入时的1/32。800正好可以被32整除变为25。但665除以32以后得到20.78,带有小数,于是RoI Pooling 直接将它量化成20。接下来需要把框内的特征池化7*7的大小,因此将上述包围框平均分割成7x7个矩形区域。显然,每个矩形区域的边长为2.86,又含有小数。于是ROI Pooling 再次把它量化到2。经过这两次量化,候选区域已经出现了较明显的偏差(如图中绿色部分所示)。更重要的是,该层特征图上0.1个像素的偏差,缩放到原图就是3.2个像素。那么0.8的偏差,在原图上就是接近30个像素点的差别,这一差别不容小觑。 -**出版源:CVPR 2018** +![](img/ch8/Mask R-CNN-02.png) -**主要链接:** +为了解决RoI Pooling的上述缺点,作者提出了RoI Align这一改进的方法(如图2)。 + +![](img/ch8/Mask R-CNN-03.png) -- arXiv:https://arxiv.org/abs/1712.00726 -- github(Official):https://github.com/zhaoweicai/cascade-rcnn +RoI Align的思路很简单:取消量化操作,使用双线性内插的方法获得坐标为浮点数的像素点上的图像数值,从而将整个特征聚集过程转化为一个连续的操作。值得注意的是,在具体的算法操作上,RoI Align并不是简单地补充出候选区域边界上的坐标点,然后将这些坐标点进行池化,而是重新设计了一套比较优雅的流程,如下图所示: +1. 遍历每一个候选区域,保持浮点数边界不做量化。 + +2. 将候选区域分割成kxk个单元,每个单元的边界也不做量化。 + +3. 在每个单元中计算固定四个坐标位置,用双线性内插的方法计算出这四个位置的值,然后进行最大池化操作。 + +这里对上述步骤的第三点作一些说明:这个固定位置是指在每一个矩形单元(bin)中按照固定规则确定的位置。比如,如果采样点数是1,那么就是这个单元的中心点。如果采样点数是4,那么就是把这个单元平均分割成四个小方块以后它们分别的中心点。显然这些采样点的坐标通常是浮点数,所以需要使用插值的方法得到它的像素值。在相关实验中,作者发现将采样点设为4会获得最佳性能,甚至直接设为1在性能上也相差无几。事实上,RoI Align 在遍历取样点的数量上没有RoI Pooling那么多,但却可以获得更好的性能,这主要归功于解决了mis alignment的问题。值得一提的是,我在实验时发现,RoI Align在VOC 2007数据集上的提升效果并不如在COCO上明显。经过分析,造成这种区别的原因是COCO上小目标的数量更多,而小目标受mis alignment问题的影响更大(比如,同样是0.5个像素点的偏差,对于较大的目标而言显得微不足道,但是对于小目标,误差的影响就要高很多)。 + +![](img/ch8/Mask R-CNN-04.png) -- [ ] TODO ## 8.3 One Stage目标检测算法 - 我们将对单次目标检测器(包括SSD、YOLO、YOLOv2、YOLOv3)进行综述。我们将分析FPN以理解多尺度特征图如何提高准确率,特别是小目标的检测,其在单次检测器中的检测效果通常很差。然后我们将分析Focal loss和RetinaNet,看看它们是如何解决训练过程中的类别不平衡问题的。 +我们将对单次目标检测器(包括SSD系列和YOLO系列等算法)进行综述。我们将分析FPN以理解多尺度特征图如何提高准确率,特别是小目标的检测,其在单次检测器中的检测效果通常很差。然后我们将分析Focal loss和RetinaNet,看看它们是如何解决训练过程中的类别不平衡问题的。 + ### 8.3.1 SSD **标题:《SSD: Single Shot MultiBox Detector》** @@ -439,7 +556,12 @@ ResNet-101+R-FCN:83.6% in PASCAL VOC 2007 test datasets - arXiv:https://arxiv.org/abs/1512.02325 - github(Official):https://github.com/weiliu89/caffe/tree/ssd -不同于前面的RCNN系列,SSD属于one-stage方法。SSD使用 VGG16 网络作为特征提取器(和 Faster R-CNN 中使用的 CNN 一样),将后面的全连接层替换成卷积层,并在之后添加自定义卷积层,并在最后直接采用卷积进行检测。在多个特征图上设置不同缩放比例和不同宽高比的default boxes(先验框)以融合多尺度特征图进行检测,靠前的大尺度特征图可以捕捉到小物体的信息,而靠后的小尺度特征图能捕捉到大物体的信息,从而提高检测的准确性和定位的准确性。如下图是SSD的网络结构图。 +**SSD有哪些创新点?** + +1. 基于Faster R-CNN中的Anchor,提出了相似的先验框(Prior box) +2. 从不同比例的特征图(多尺度特征)中产生不同比例的预测,并明确地按长宽比分离预测。 + +不同于前面的R-CNN系列,SSD属于one-stage方法。SSD使用 VGG16 网络作为特征提取器(和 Faster R-CNN 中使用的 CNN 一样),将后面的全连接层替换成卷积层,并在之后添加自定义卷积层,并在最后直接采用卷积进行检测。在多个特征图上设置不同缩放比例和不同宽高比的先验框以融合多尺度特征图进行检测,靠前的大尺度特征图可以捕捉到小物体的信息,而靠后的小尺度特征图能捕捉到大物体的信息,从而提高检测的准确性和定位的准确性。如下图是SSD的网络结构图。 ![](./img/ch8/SSD-01.png) @@ -462,8 +584,6 @@ SSD在训练的时候只需要输入图像和图像中每个目标对应的groun 最后分别在所选的特征层上使用3x3卷积核预测不同default boxes所属的类别分数及其预测的边界框location。由于对于每个box需要预测该box属于每个类别的置信度(假设有c类,包括背景)和该box对应的预测边界框的location(包含4个值,即该box的中心坐标和宽高),则每个box需要预测c+4个值。所以对于某个所选的特征层,该层的卷积核个数为(c+4)x该层的default box个数.最后将每个层得到的卷积结果进行拼接。对于得到的每个预测框,取其类别置信度的最大值,若该最大值大于置信度阈值,则最大值所对应的类别即为该预测框的类别,否则过滤掉此框。对于保留的预测框根据它对应的先验框进行解码得到其真实的位置参数(这里还需注意要防止预测框位置超出图片),然后根据所属类别置信度进行降序排列,取top-k个预测框,最后进行NMS,过滤掉重叠度较大的预测框,最后得到检测结果。 - - SSD优势是速度比较快,整个过程只需要一步,首先在图片不同位置按照不同尺度和宽高比进行密集抽样,然后利用CNN提取特征后直接进行分类与回归,所以速度比较快,但均匀密集采样会造成正负样本不均衡的情况使得训练比较困难,导致模型准确度有所降低。另外,SSD对小目标的检测没有大目标好,因为随着网络的加深,在高层特征图中小目标的信息丢失掉了,适当增大输入图片的尺寸可以提升小目标的检测效果。 ### 8.3.2 DSSD @@ -479,28 +599,32 @@ SSD优势是速度比较快,整个过程只需要一步,首先在图片不 - arXiv:https://arxiv.org/abs/1701.06659 - github(Official):https://github.com/chengyangfu/caffe/tree/dssd +**DSSD有哪些创新点?** +1. Backbone:将ResNet替换SSD中的VGG网络,增强了特征提取能力 +2. 添加了Deconvolution层,增加了大量上下文信息 +为了解决SSD算法检测小目标困难的问题,DSSD算法将SSD算法基础网络从VGG-16更改为ResNet-101,增强网络特征提取能力,其次参考FPN算法思路利用去Deconvolution结构将图像深层特征从高维空间传递出来,与浅层信息融合,联系不同层级之间的图像语义关系,设计预测模块结构,通过不同层级特征之间融合特征输出预测物体类别信息。 -- [ ] TODO +DSSD算法中有两个特殊的结构:Prediction模块;Deconvolution模块。前者利用提升每个子任务的表现来提高准确性,并且防止梯度直接流入ResNet主网络。后者则增加了三个Batch Normalization层和三个3×3卷积层,其中卷积层起到了缓冲的作用,防止梯度对主网络影响太剧烈,保证网络的稳定性。 -### 8.3.3 FSSD +SSD和DSSD的网络模型如下图所示: -**标题:《FSSD: Feature Fusion Single Shot Multibox Detector》** +![](img/ch8/DSSD-01.png) -**时间:2017** +**Prediction Module** -**出版源:None** +SSD直接从多个卷积层中单独引出预测函数,预测量多达7000多,梯度计算量也很大。MS-CNN方法指出,改进每个任务的子网可以提高准确性。根据这一思想,DSSD在每一个预测层后增加残差模块,并且对于多种方案进行了对比,如下图所示。结果表明,增加残差预测模块后,高分辨率图片的检测精度比原始SSD提升明显。 -**主要链接:** +![](img/ch8/DSSD-02.png) -- arXiv:https://arxiv.org/abs/1712.00960 +**Deconvolution模块** +为了整合浅层特征图和deconvolution层的信息,作者引入deconvolution模块,如下图所示。作者受到论文Learning to Refine Object Segments的启发,认为用于精细网络的deconvolution模块的分解结构达到的精度可以和复杂网络一样,并且更有效率。作者对其进行了一定的修改:其一,在每个卷积层后添加批归一化(batch normalization)层;其二,使用基于学习的deconvolution层而不是简单地双线性上采样;其三,作者测试了不同的结合方式,元素求和(element-wise sum)与元素点积(element-wise product)方式,实验证明元素点积计算能得到更好的精度。 +![](img/ch8/DSSD-03.png) -- [ ] TODO - -### 8.3.4 YOLOv1 +### 8.3.3 YOLOv1 **标题:《You Only Look Once: Unified, Real-Time Object Detection》** @@ -513,6 +637,11 @@ SSD优势是速度比较快,整个过程只需要一步,首先在图片不 - arXiv:http://arxiv.org/abs/1506.02640 - github(Official):https://github.com/pjreddie/darknet +**YOLOv1有哪些创新点?** + +1. 将整张图作为网络的输入,直接在输出层回归bounding box的位置和所属的类别 +2. 速度快,one stage detection的开山之作 + **YOLOv1介绍** YOLO(You Only Look Once: Unified, Real-Time Object Detection)是one-stage detection的开山之作。之前的物体检测方法首先需要产生大量可能包含待检测物体的先验框, 然后用分类器判断每个先验框对应的边界框里是否包含待检测物体,以及物体所属类别的概率或者置信度,同时需要后处理修正边界框,最后基于一些准则过滤掉置信度不高和重叠度较高的边界框,进而得到检测结果。这种基于先产生候选区再检测的方法虽然有相对较高的检测准确率,但运行速度较慢。 @@ -523,8 +652,6 @@ YOLO创造性的将物体检测任务直接当作回归问题(regression probl 事实上,YOLO也并没有真正的去掉候选区,而是直接将输入图片划分成7x7=49个网格,每个网格预测两个边界框,一共预测49x2=98个边界框。可以近似理解为在输入图片上粗略的选取98个候选区,这98个候选区覆盖了图片的整个区域,进而用回归预测这98个候选框对应的边界框。 -**下面以问答的形式展示YOLO中的一些实现细节:** - **1. 网络结构是怎样的?** YOLO网络借鉴了GoogleNet分类网络结构,不同的是YOLO使用1x1卷积层和3x3卷积层替代inception module。如下图所示,整个检测网络包括24个卷积层和2个全连接层。其中,卷积层用来提取图像特征,全连接层用来预测图像位置和类别概率值。 @@ -576,7 +703,7 @@ YOLO将识别与定位合二为一,结构简便,检测速度快,更快的F 由于YOLO网格设置比较稀疏,且每个网格只预测2个边界框,其总体预测精度不高,略低于Fast RCNN。其对小物体的检测效果较差,尤其是对密集的小物体表现比较差。 -### 8.3.5 YOLOv2 +### 8.3.4 YOLOv2 **标题:《YOLO9000: Better, Faster, Stronger》** @@ -589,7 +716,13 @@ YOLO将识别与定位合二为一,结构简便,检测速度快,更快的F - arXiv:https://arxiv.org/abs/1612.08242 - github(Official):https://pjreddie.com/darknet/yolov2/ -YOLOv1虽然检测速度快,但在定位方面不够准确,并且召回率较低。为了提升定位准确度,改善召回率,YOLOv2在YOLOv1的基础上提出了几种改进策略,如下图所示,可以看到,一些改进方法能有效提高模型的mAP. +**YOLOv2 有哪些创新点?** + +YOLOv1虽然检测速度快,但在定位方面不够准确,并且召回率较低。为了提升定位准确度,改善召回率,YOLOv2在YOLOv1的基础上提出了几种改进策略,如下图所示,可以看到,一些改进方法能有效提高模型的mAP。 + +1. 大尺度预训练分类 +2. New Network:Darknet-19 +3. 加入anchor ![](./img/ch8/YOLOv2-01.png) @@ -644,7 +777,7 @@ YOLOv2的训练主要包括三个阶段。 第三个阶段:修改Darknet-19分类模型为检测模型,并在检测数据集上继续finetune网络。 网络修改包括(网路结构可视化):移除最后一个卷积层、global avgpooling层以及softmax层,并且新增了三个3*3*2014卷积层,同时增加了一个passthrough层,最后使用1*1卷积层输出预测结果。 -### 8.3.6 YOLO9000 +### 8.3.5 YOLO9000 github:http://pjreddie.com/yolo9000/ @@ -677,7 +810,7 @@ WordTree中每个节点的子节点都属于同一个子类,分层次的对每 YOLO9000使用WordTree混合目标检测数据集和分类数据集,并在其上进行联合训练,使之能实时检测出超过9000个类别的物体,其强大令人赞叹不已。YOLO9000尤其对动物的识别效果很好,但是对衣服或者设备等类别的识别效果不是很好,可能的原因是与目标检测数据集中的数据偏向有关。 -### 8.3.7 YOLOv3 +### 8.3.6 YOLOv3 **标题:《YOLOv3: An Incremental Improvement》** @@ -692,6 +825,12 @@ YOLO9000使用WordTree混合目标检测数据集和分类数据集,并在其 YOLOv3总结了自己在YOLOv2的基础上做的一些尝试性改进,有的尝试取得了成功,而有的尝试并没有提升模型性能。其中有两个值得一提的亮点,一个是使用残差模型,进一步加深了网络结构;另一个是使用FPN架构实现多尺度检测。 +**YOLOv3有哪些创新点?** + +1. 新网络结构:DarkNet-53 +2. 融合FPN +3. 用逻辑回归替代softmax作为分类器 + **1. YOLOv3对网络结构做了哪些改进?** YOLOv3在之前Darknet-19的基础上引入了残差块,并进一步加深了网络,改进后的网络有53个卷积层,取名为Darknet-53,网络结构如下图所示(以256*256的输入为例)。 @@ -710,7 +849,7 @@ YOLOv3借鉴了FPN的思想,从不同尺度提取特征。相比YOLOv2,YOLOv 从YOLOv1到YOLOv2再到YOLO9000、YOLOv3, YOLO经历三代变革,在保持速度优势的同时,不断改进网络结构,同时汲取其它优秀的目标检测算法的各种trick,先后引入anchor box机制、引入FPN实现多尺度检测等。 -### 8.3.8 RetinaNet +### 8.3.7 RetinaNet **标题:《Focal Loss for Dense Object Detection》** @@ -756,7 +895,7 @@ YOLOv3借鉴了FPN的思想,从不同尺度提取特征。相比YOLOv2,YOLOv 答:因为通过RPN阶段可以减少候选目标区域,而在分类阶段,可以固定前景与背景比值(foreground-to-background ratio)为1:3,或者使用OHEM(online hard example mining)使得前景和背景的数量达到均衡。 -**RetinaNet 创新点** +**RetinaNet有哪些创新点?** **概述:** @@ -875,7 +1014,7 @@ Table1是关于RetinaNet和Focal Loss的一些实验结果。(a)是在交叉 ![](./img/ch8/RetinaNet-14.png) -### 8.3.9 RFBNet +### 8.3.8 RFBNet **标题:《Receptive Field Block Net for Accurate and Fast Object Detection》** @@ -889,11 +1028,32 @@ arXiv:https://arxiv.org/pdf/1711.07767.pdf github(Official):https://github.com/ruinmessi/RFBNet +**RFBNet有哪些创新点?** + +1. 提出RF block(RFB)模块 + +RFBNet主要想利用一些技巧使得轻量级模型在速度和精度上达到很好的trade-off的检测器。灵感来自人类视觉的感受野结构Receptive Fields (RFs) ,提出了新奇的RF block(RFB)模块,来验证感受野尺寸和方向性的对提高有鉴别鲁棒特征的关系。RFBNet是以主干网络(backbone)为VGG16的SSD来构建的,主要是在Inception的基础上加入了dilated卷积层(dilated convolution),从而有效增大了感受野(receptive field)。整体上因为是基于SSD网络进行改进,所以检测速度还是比较快,同时精度也有一定的保证。 + +**RFB介绍** + +RFB是一个类似Inception模块的多分支卷积模块,它的内部结构可分为两个组件:多分支卷积层和dilated卷积层。如下图: + +![](img/ch8/RFBNet-01.png) + +**1.多分支卷积层** +​ 根据RF的定义,用多种尺寸的卷积核来实现比固定尺寸更好。具体设计:1.瓶颈结构,1x1-s2卷积减少通道特征,然后加上一个nxn卷积。2.替换5x5卷积为两个3x3卷积去减少参数,然后是更深的非线性层。有些例子,使用1xn和nx1代替nxn卷积;shortcut直连设计来自于ResNet和Inception ResNet V2。3.为了输出,卷积经常有stride=2或者是减少通道,所以直连层用一个不带非线性激活的1x1卷积层。 + +**2.Dilated 卷积层** + +设计灵感来自Deeplab,在保持参数量和同样感受野的情况下,用来获取更高分辨率的特征。下图展示两种RFB结构:RFB和RFB-s。每个分支都是一个正常卷积后面加一个dilated卷积,主要是尺寸和dilated因子不同。(a)RFB。整体结构上借鉴了Inception的思想,主要不同点在于引入3个dilated卷积层(比如3x3conv,rate=1),这也是RFBNet增大感受野的主要方式之一;(b)RFB-s。RFB-s和RFB相比主要有两个改进,一方面用3x3卷积层代替5x5卷积层,另一方面用1x3和3x1卷积层代替3x3卷积层,主要目的应该是为了减少计算量,类似Inception后期版本对Inception结构的改进。 + +![](img/ch8/RFBNet-02.png) +RFBNet300的整体结构如下图所示,基本上和SSD类似。RFBNet和SSD不同的是:1、主干网上用两个RFB结构替换原来新增的两层。2、conv4_3和conv7_fc在接预测层之前分别接RFB-s和RFB结构。 -- [ ] TODO +![](img/ch8/RFBNet-03.png) -### 8.3.10 M2Det +### 8.3.9 M2Det **标题:《M2Det: A Single-Shot Object Detector based on Multi-Level Feature Pyramid Network》** @@ -906,6 +1066,31 @@ github(Official):https://github.com/ruinmessi/RFBNet - arXiv:https://arxiv.org/abs/1811.04533 - github(Official):https://github.com/qijiezhao/M2Det +**M2Det有哪些创新点?** + +1. 提出了多层次特征金字塔网络(MLFPN)来构建更有效的特征金字塔,用于检测不同尺度的对象。 + +M2Det的整体架构如下所示。M2Det使用backbone和多级特征金字塔网络(MLFPN)从输入图像中提取特征,然后类似于SSD,根据学习的特征生成密集的边界框和类别分数,最后是非最大抑制(NMS)操作以产生最终结果。 MLFPN由三个模块组成:特征融合模块(FFM),简化的U形模块(TUM)和按基于尺度的特征聚合模块(SFAM)。 FFMv1通过融合骨干网络的特征图,将语义信息丰富为基本特征。每个TUM生成一组多尺度特征,然后交替连接的TUM和FFMv2提取多级多尺度特征。此外,SFAM通过按比例缩放的特征连接操作和自适应注意机制将特征聚合到多级特征金字塔中。下面介绍有关M2Det中三个核心模块和网络配置的更多详细信息。 + +![](img/ch8/M2Det-01.png) + +**FFMs** + +FFM融合了M2Det中不同层次的特征,这对于构建最终的多级特征金字塔至关重要。它们使用1x1卷积层来压缩输入特征的通道,并使用连接操作来聚合这些特征图。特别是,由于FFMv1以backbone中不同比例的两个特征图作为输入,因此它采用一个上采样操作,在连接操作之前将深度特征重新缩放到相同的尺度。同时,FFMv2采用基本特征和前一个TUM的最大输出特征图 - 这两个具有相同的比例 - 作为输入,并产生下一个TUM的融合特征。 FFMv1和FFMv2的结构细节分别如下图(a)和(b)所示。 + +![](img/ch8/M2Det-02.png) + +**TUMs** + +TUM不同于FPN和RetinaNet,TUM采用简化的U形结构,如上图(c)所示。编码器是一系列3x3,步长为2的卷积层.并且解码器将这些层的输出作为其参考特征集,而原始FPN选择ResNet主干网络中每个阶段的最后一层的输出。此外,在解码器分支的上采样层后添加1x1卷积层和按元素求和的操作,以增强学习能力并保持特征的平滑性。每个TUM的解码器中的所有输出形成当前级别的多尺度特征。整体而言,堆叠TUM的输出形成多层次多尺度特征,而前TUM主要提供浅层特征,中间TUM提供中等特征,后TUM提供深层特征。 + +**SFAM** + +SFAM旨在将由TUM生成的多级多尺度特征聚合成多级特征金字塔,如下图所示。SFAM的第一阶段是沿着信道维度将等效尺度的特征连接在一起。聚合特征金字塔可以表示为X = [X1,X2,...,Xi],其中Xi = Concat(x1i,x2i,...,xLi +) ∈ RWi×Hi×C指的是尺度第i个最大的特征。这里,聚合金字塔中的每个比例都包含来自多级深度的特征。但是,简单的连接操作不太适合。在第二阶段,引入了通道注意模块,以促使特征集中在最有益的通道。在SE区块之后,使用全局平均池化来在挤压步骤中生成通道统计z∈RC。 + +![](img/ch8/M2Det-03.png) + ## 8.4 人脸检测 在目标检测领域可以划分为了人脸检测与通用目标检测,往往人脸这方面会有专门的算法(包括人脸检测、人脸识别、人脸其他属性的识别等等),并且和通用目标检测(识别)会有一定的差别,着主要来源于人脸的特殊性(有时候目标比较小、人脸之间特征不明显、遮挡问题等),下面将从人脸检测和通用目标检测两个方面来讲解目标检测。 @@ -964,7 +1149,7 @@ github(Official):https://github.com/ruinmessi/RFBNet 原理类似,这里主要看anchorbox的最小box,通过可以通过缩放输入图片实现最小人脸的设定。 -### 8.4.4 如何定位人脸的位置 +### 8.4.4 如何定位人脸的位置? (1)滑动窗的方式: @@ -982,7 +1167,7 @@ github(Official):https://github.com/ruinmessi/RFBNet ​ 通过特征图映射到图的窗口,通过特征图映射到原图到多个框的方式确定最终识别为人脸的位置。 -### 8.1.5 如何通过一个人脸的多个框确定最终人脸框位置? +### 8.4.5 如何通过一个人脸的多个框确定最终人脸框位置? ![](./img/ch8/8.4.5.png) @@ -990,7 +1175,7 @@ github(Official):https://github.com/ruinmessi/RFBNet NMS改进版本有很多,最原始的NMS就是判断两个框的交集,如果交集大于设定的阈值,将删除其中一个框,那么两个框应该怎么选择删除哪一个呢? 因为模型输出有概率值,一般会优选选择概率小的框删除。 -### 8.1.6 基于级联卷积神经网络的人脸检测(Cascade CNN) +### 8.4.6 基于级联卷积神经网络的人脸检测(Cascade CNN) 1. cascade cnn的框架结构是什么? @@ -1082,7 +1267,46 @@ $$ +## 8.5 目标检测的技巧汇总 + +1. Data Augmentation +2. OHEM +3. NMS:Soft NMS/ Polygon NMS/ Inclined NMS/ ConvNMS/ Yes-Net NMS/ Softer NMS +4. Multi Scale Training/Testing +5. 建立小物体与context的关系 +6. 参考relation network +7. 结合GAN +8. 结合attention + +## 8.6 目标检测的常用数据集 +### 8.6.1 PASCAL VOC + +VOC数据集是目标检测经常用的一个数据集,自2005年起每年举办一次比赛,最开始只有4类,到2007年扩充为20个类,共有两个常用的版本:2007和2012。学术界常用5k的train/val 2007和16k的train/val 2012作为训练集,test 2007作为测试集,用10k的train/val 2007+test 2007和16k的train/val 2012作为训练集,test2012作为测试集,分别汇报结果。 + +### 8.6.2 MS COCO + +COCO数据集是微软团队发布的一个可以用来图像recognition+segmentation+captioning 数据集,该数据集收集了大量包含常见物体的日常场景图片,并提供像素级的实例标注以更精确地评估检测和分割算法的效果,致力于推动场景理解的研究进展。依托这一数据集,每年举办一次比赛,现已涵盖检测、分割、关键点识别、注释等机器视觉的中心任务,是继ImageNet Chanllenge以来最有影响力的学术竞赛之一。 + +相比ImageNet,COCO更加偏好目标与其场景共同出现的图片,即non-iconic images。这样的图片能够反映视觉上的语义,更符合图像理解的任务要求。而相对的iconic images则更适合浅语义的图像分类等任务。 + +COCO的检测任务共含有80个类,在2014年发布的数据规模分train/val/test分别为80k/40k/40k,学术界较为通用的划分是使用train和35k的val子集作为训练集(trainval35k),使用剩余的val作为测试集(minival),同时向官方的evaluation server提交结果(test-dev)。除此之外,COCO官方也保留一部分test数据作为比赛的评测集。 + +### 8.6.3 Google Open Image + +Open Image是谷歌团队发布的数据集。最新发布的Open Images V4包含190万图像、600个种类,1540万个bounding-box标注,是当前最大的带物体位置标注信息的数据集。这些边界框大部分都是由专业注释人员手动绘制的,确保了它们的准确性和一致性。另外,这些图像是非常多样化的,并且通常包含有多个对象的复杂场景(平均每个图像 8 个)。 + +### 8.6.4 ImageNet + +ImageNet是一个计算机视觉系统识别项目, 是目前世界上图像识别最大的数据库。ImageNet是美国斯坦福的计算机科学家,模拟人类的识别系统建立的。能够从图片识别物体。Imagenet数据集文档详细,有专门的团队维护,使用非常方便,在计算机视觉领域研究论文中应用非常广,几乎成为了目前深度学习图像领域算法性能检验的“标准”数据集。Imagenet数据集有1400多万幅图片,涵盖2万多个类别;其中有超过百万的图片有明确的类别标注和图像中物体位置的标注。 + +## TODO + +- [ ] 目标检测基础知识:mAP、IoU和NMS等 +- [ ] 目标检测评测指标 +- [ ] 目标检测常见标注工具 +- [ ] 完善目标检测的技巧汇总 +- [ ] 目标检测的现在难点和未来发展 ## Reference @@ -1091,3 +1315,9 @@ https://github.com/amusi/awesome-object-detection https://github.com/hoya012/deep_learning_object_detection https://handong1587.github.io/deep_learning/2015/10/09/object-detection.html + +https://www.zhihu.com/question/272322209/answer/482922713 + +http://blog.leanote.com/post/afanti.deng@gmail.com/b5f4f526490b + +https://blog.csdn.net/hw5226349/article/details/78987385 \ No newline at end of file diff --git "a/ch09_\345\233\276\345\203\217\345\210\206\345\211\262/img/ch9/9-10-2.jpg" "b/ch09_\345\233\276\345\203\217\345\210\206\345\211\262/img/ch9/9-10-2.jpg" deleted file mode 100644 index 2d1a937d..00000000 Binary files "a/ch09_\345\233\276\345\203\217\345\210\206\345\211\262/img/ch9/9-10-2.jpg" and /dev/null differ diff --git "a/ch09_\345\233\276\345\203\217\345\210\206\345\211\262/img/ch9/9-10-2.png" "b/ch09_\345\233\276\345\203\217\345\210\206\345\211\262/img/ch9/9-10-2.png" new file mode 100644 index 00000000..03d036ff Binary files /dev/null and "b/ch09_\345\233\276\345\203\217\345\210\206\345\211\262/img/ch9/9-10-2.png" differ diff --git "a/ch09_\345\233\276\345\203\217\345\210\206\345\211\262/img/ch9/COCO-01.png" "b/ch09_\345\233\276\345\203\217\345\210\206\345\211\262/img/ch9/COCO-01.png" new file mode 100644 index 00000000..e9e4aef4 Binary files /dev/null and "b/ch09_\345\233\276\345\203\217\345\210\206\345\211\262/img/ch9/COCO-01.png" differ diff --git "a/ch09_\345\233\276\345\203\217\345\210\206\345\211\262/img/ch9/Cityscapes-01.png" "b/ch09_\345\233\276\345\203\217\345\210\206\345\211\262/img/ch9/Cityscapes-01.png" new file mode 100644 index 00000000..d29e608b Binary files /dev/null and "b/ch09_\345\233\276\345\203\217\345\210\206\345\211\262/img/ch9/Cityscapes-01.png" differ diff --git "a/ch09_\345\233\276\345\203\217\345\210\206\345\211\262/img/ch9/Instance-01.png" "b/ch09_\345\233\276\345\203\217\345\210\206\345\211\262/img/ch9/Instance-01.png" new file mode 100644 index 00000000..e063a032 Binary files /dev/null and "b/ch09_\345\233\276\345\203\217\345\210\206\345\211\262/img/ch9/Instance-01.png" differ diff --git "a/ch09_\345\233\276\345\203\217\345\210\206\345\211\262/img/ch9/VOC-01.png" "b/ch09_\345\233\276\345\203\217\345\210\206\345\211\262/img/ch9/VOC-01.png" new file mode 100644 index 00000000..a0f02fdd Binary files /dev/null and "b/ch09_\345\233\276\345\203\217\345\210\206\345\211\262/img/ch9/VOC-01.png" differ diff --git "a/ch09_\345\233\276\345\203\217\345\210\206\345\211\262/img/ch9/semantic-01.png" "b/ch09_\345\233\276\345\203\217\345\210\206\345\211\262/img/ch9/semantic-01.png" new file mode 100644 index 00000000..8223f766 Binary files /dev/null and "b/ch09_\345\233\276\345\203\217\345\210\206\345\211\262/img/ch9/semantic-01.png" differ diff --git "a/ch09_\345\233\276\345\203\217\345\210\206\345\211\262/modify_log.txt" "b/ch09_\345\233\276\345\203\217\345\210\206\345\211\262/modify_log.txt" index cffcd2de..4f180f95 100644 --- "a/ch09_\345\233\276\345\203\217\345\210\206\345\211\262/modify_log.txt" +++ "b/ch09_\345\233\276\345\203\217\345\210\206\345\211\262/modify_log.txt" @@ -34,11 +34,12 @@ modify_log---->用来记录修改日志 <----qjhuang-2018-11-9----> 1. 修改部分答案公式,链接 -<----qjhuang-2019-3-15----> -1. 修改图片错别字 - 其他---->待增加 2. 修改readme内容 3. 修改modify内容 4. 修改章节内容,图片路径等 +<----cfj-2019-01-07----> + +1. 新增什么是图像分割?图像分割算法类别 +2. 新增图像分割数据集 \ No newline at end of file diff --git "a/ch09_\345\233\276\345\203\217\345\210\206\345\211\262/readme.md" "b/ch09_\345\233\276\345\203\217\345\210\206\345\211\262/readme.md" index 26409571..fc3e1b3e 100644 --- "a/ch09_\345\233\276\345\203\217\345\210\206\345\211\262/readme.md" +++ "b/ch09_\345\233\276\345\203\217\345\210\206\345\211\262/readme.md" @@ -6,9 +6,11 @@ 电子科大研究生-孙洪卫(wechat:sunhwee,email:hwsun@std.uestc.edu.cn) 电子科大研究生-张越(wechat:tianyuzy) 华南理工研究生-黄钦建(wechat:HQJ199508212176,email:csqjhuang@mail.scut.edu.cn) -中国农业科学院-杨国峰(wechat:tectal,email:yangguofeng@caas.cn) +中国农业科学院-杨国峰() + +上海大学-陈方杰(wechat:cfj123456cfj,email:1609951733@qq.com) **贡献者(排名不分先后):** 内容贡献者可自加信息 -########################################################### +########################################################### \ No newline at end of file diff --git "a/ch09_\345\233\276\345\203\217\345\210\206\345\211\262/\347\254\254\344\271\235\347\253\240_\345\233\276\345\203\217\345\210\206\345\211\262.md" "b/ch09_\345\233\276\345\203\217\345\210\206\345\211\262/\347\254\254\344\271\235\347\253\240_\345\233\276\345\203\217\345\210\206\345\211\262.md" index 992d4c79..5704bc1c 100644 --- "a/ch09_\345\233\276\345\203\217\345\210\206\345\211\262/\347\254\254\344\271\235\347\253\240_\345\233\276\345\203\217\345\210\206\345\211\262.md" +++ "b/ch09_\345\233\276\345\203\217\345\210\206\345\211\262/\347\254\254\344\271\235\347\253\240_\345\233\276\345\203\217\345\210\206\345\211\262.md" @@ -1,24 +1,40 @@ - [TOC] -``` 作者:scutan90 编辑者:shw2018(UESTC_孙洪卫_硕,Wechat:sunhwee) 提交:2018.10.25 更新:2018.10.31 -``` + +<----cfj-2019-01-07----> + +1. 新增什么是图像分割?图像分割算法类别 +2. 新增图像分割数据集 # 第九章 图像分割 -## 9.1 传统的基于CNN的分割方法缺点? +## 9.1 什么是图像分割? + +图像分割是预测图像中每一个像素所属的类别或者物体。 + +## 9.2 图像分割算法分类? + +基于深度学习的图像分割算法主要分为两类: + +**1.语义分割** + +为图像中的每个像素分配一个类别,如把画面中的所有物体都指出它们各自的类别。 + +![](./img/ch9/Semantic-01.png) + +**2.实例分割** + +与语义分割不同,实例分割只对特定物体进行类别分配,这一点与目标检测有点相似,但目标检测输出的是边界框和类别,而实例分割输出的是掩膜(mask)和类别。 + +![](./img/ch9/Instance-01.png) + +## 9.3 传统的基于CNN的分割方法缺点?    传统的基于CNN的分割方法:为了对一个像素分类,使用该像素周围的一个图像块作为CNN的输入,用于训练与预测,这种方法主要有几个缺点: @@ -765,7 +781,7 @@ DenseNet的Block结构如上图所示。    1*1卷积核的目的:减少输入的特征图数量,这样既能降维减少计算量,又能融合各个通道的特征。我们将使用BottleNeck Layers的DenseNet表示为DenseNet-B。(在论文的实验里,将1×1×n小卷积里的n设置为4k,k为每个H产生的特征图数量) -![](./img/ch9/9-10-2.jpg) +![](./img/ch9/9-10-2.png)    上图是DenseNet网络的整体网络结构示意图。其中1*1卷积核的目的是进一步压缩参数,并且在Transition Layer层有个参数Reduction(范围是0到1),表示将这些输出缩小到原来的多少倍,默认是0.5,这样传给下一个Dense Block的时候channel数量就会减少一半。当Reduction的值小于1的时候,我们就把带有这种层的网络称为DenseNet-C。 @@ -777,3 +793,37 @@ DenseNet网络的优点包括: - 更有效地利用了feature  - 一定程度上较少了参数数量 - 一定程度上减轻了过拟合 + +## 9.12 图像分割的常用数据集 + +### 9.12.1 PASCAL VOC + +VOC 数据集分为20类,包括背景为21类,分别如下: +- Person: person +- Animal: bird, cat, cow, dog, horse, sheep +- Vehicle: aeroplane, bicycle, boat, bus, car, motorbike, train +- Indoor: bottle, chair, dining table, potted plant, sofa, tv/monitor + +VOC 数据集中用于分割比赛的图片实例如下,包含原图以及图像分类分割和图像物体分割两种图(PNG格式)。图像分类分割是在20种物体中,ground-turth图片上每个物体的轮廓填充都有一个特定的颜色,一共20种颜色。 + +![](./img/ch9/VOC-01.png) + +### 9.12.2 MS COCO + +MS COCO 是最大图像分割数据集,提供的类别有 80 类,有超过 33 万张图片,其中 20 万张有标注,整个数据集中个体的数目超过 150 万个。MS COCO是目前难度最大,挑战最高的图像分割数据集。 + +![](./img/ch9/COCO-01.png) + +### 9.12.3 Cityscapes + +Cityscapes 是驾驶领域进行效果和性能测试的图像分割数据集,它包含了5000张精细标注的图像和20000张粗略标注的图像,这些图像包含50个城市的不同场景、不同背景、不同街景,以及30类涵盖地面、建筑、交通标志、自然、天空、人和车辆等的物体标注。Cityscapes评测集有两项任务:像素级(Pixel-level)图像场景分割(以下简称语义分割)与实例级(Instance-level)图像场景分割(以下简称实例分割)。 + +![](./img/ch9/Cityscapes-01.png) + +TODO + +- [ ] 图像分割数据集标注工具 +- [ ] 图像分割评价标准 +- [ ] 全景分割 +- [ ] UNet++ + diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/._.DS_Store" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/._.DS_Store" new file mode 100644 index 00000000..a5b28df1 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/._.DS_Store" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/._ch11.pdf" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/._ch11.pdf" new file mode 100644 index 00000000..010454ac Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/._ch11.pdf" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/._img" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/._img" new file mode 100644 index 00000000..87b62765 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/._img" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/._media" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/._media" new file mode 100644 index 00000000..87b62765 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/._media" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/._\347\254\254\345\215\201\344\270\200\347\253\240_\350\277\201\347\247\273\345\255\246\344\271\240.md" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/._\347\254\254\345\215\201\344\270\200\347\253\240_\350\277\201\347\247\273\345\255\246\344\271\240.md" new file mode 100644 index 00000000..2d70b75b Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/._\347\254\254\345\215\201\344\270\200\347\253\240_\350\277\201\347\247\273\345\255\246\344\271\240.md" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/img/._.DS_Store" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/img/._.DS_Store" new file mode 100644 index 00000000..a5b28df1 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/img/._.DS_Store" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/img/._ch11" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/img/._ch11" new file mode 100644 index 00000000..87b62765 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/img/._ch11" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/img/ch11/._1542972502781.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/img/ch11/._1542972502781.png" new file mode 100644 index 00000000..eb9a1600 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/img/ch11/._1542972502781.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/img/ch11/._1542973960796.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/img/ch11/._1542973960796.png" new file mode 100644 index 00000000..6c1e5125 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/img/ch11/._1542973960796.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/img/ch11/._1542974131814.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/img/ch11/._1542974131814.png" new file mode 100644 index 00000000..8459a8b6 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/img/ch11/._1542974131814.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/img/ch11/._readme.md" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/img/ch11/._readme.md" new file mode 100644 index 00000000..74aad09d Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/img/ch11/._readme.md" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._00864b9c79b810761fec244e89a0ea08.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._00864b9c79b810761fec244e89a0ea08.jpg" new file mode 100644 index 00000000..b7f20e60 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._00864b9c79b810761fec244e89a0ea08.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._02cf7802ec9aabdccf710442cda04ccb.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._02cf7802ec9aabdccf710442cda04ccb.jpg" new file mode 100644 index 00000000..38e20806 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._02cf7802ec9aabdccf710442cda04ccb.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._07e7da7afdea5c38f470b3a06d8137e2.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._07e7da7afdea5c38f470b3a06d8137e2.jpg" new file mode 100644 index 00000000..002bc7ca Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._07e7da7afdea5c38f470b3a06d8137e2.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._0854b7278c50c5e2b0bbe61d273721c1.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._0854b7278c50c5e2b0bbe61d273721c1.jpg" new file mode 100644 index 00000000..405346b4 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._0854b7278c50c5e2b0bbe61d273721c1.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._09cb64cf3f3ceb5d87369e41c29d34bf.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._09cb64cf3f3ceb5d87369e41c29d34bf.jpg" new file mode 100644 index 00000000..b38249ac Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._09cb64cf3f3ceb5d87369e41c29d34bf.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._0b5d1ded61af9b38fedb2746a7dda23e.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._0b5d1ded61af9b38fedb2746a7dda23e.jpg" new file mode 100644 index 00000000..61850f02 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._0b5d1ded61af9b38fedb2746a7dda23e.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._0f3a57ffdefd178a4db06b52c2d53b58.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._0f3a57ffdefd178a4db06b52c2d53b58.jpg" new file mode 100644 index 00000000..8375be5b Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._0f3a57ffdefd178a4db06b52c2d53b58.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._103de3658cbb97ad4c24bafe28f9d957.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._103de3658cbb97ad4c24bafe28f9d957.jpg" new file mode 100644 index 00000000..671beac5 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._103de3658cbb97ad4c24bafe28f9d957.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542808441403.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542808441403.png" new file mode 100644 index 00000000..7d68c773 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542808441403.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542812321831.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542812321831.png" new file mode 100644 index 00000000..ee67a092 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542812321831.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542812440636.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542812440636.png" new file mode 100644 index 00000000..f735f9df Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542812440636.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542812748062.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542812748062.png" new file mode 100644 index 00000000..94ba806f Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542812748062.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542817257337.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542817257337.png" new file mode 100644 index 00000000..7ae49643 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542817257337.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542817481582.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542817481582.png" new file mode 100644 index 00000000..9b5559f2 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542817481582.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542820738631.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542820738631.png" new file mode 100644 index 00000000..b99d132f Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542820738631.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542820752570.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542820752570.png" new file mode 100644 index 00000000..e58f76da Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542820752570.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542820774326.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542820774326.png" new file mode 100644 index 00000000..6a4622ed Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542820774326.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542820797637.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542820797637.png" new file mode 100644 index 00000000..cbd806f9 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542820797637.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542821989163.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542821989163.png" new file mode 100644 index 00000000..1fa3c0ec Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542821989163.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542822045307.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542822045307.png" new file mode 100644 index 00000000..2b9c4acf Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542822045307.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542822087844.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542822087844.png" new file mode 100644 index 00000000..79726140 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542822087844.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542822226596.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542822226596.png" new file mode 100644 index 00000000..25b363ea Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542822226596.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542822305161.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542822305161.png" new file mode 100644 index 00000000..e8d93155 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542822305161.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542822326035.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542822326035.png" new file mode 100644 index 00000000..b58802fe Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542822326035.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542822355361.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542822355361.png" new file mode 100644 index 00000000..83f4dd2c Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542822355361.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542822398717.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542822398717.png" new file mode 100644 index 00000000..ce317974 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542822398717.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542822474045.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542822474045.png" new file mode 100644 index 00000000..1174a5f0 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542822474045.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542822558549.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542822558549.png" new file mode 100644 index 00000000..7d1723c6 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542822558549.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542822578502.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542822578502.png" new file mode 100644 index 00000000..1aa0211b Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542822578502.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542822851294.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542822851294.png" new file mode 100644 index 00000000..3c27a230 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542822851294.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542822971212.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542822971212.png" new file mode 100644 index 00000000..c0fcc725 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542822971212.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542823019007.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542823019007.png" new file mode 100644 index 00000000..2e0dca48 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542823019007.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542823210556.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542823210556.png" new file mode 100644 index 00000000..48b1fd1e Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542823210556.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542823438846.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542823438846.png" new file mode 100644 index 00000000..6fc808dd Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542823438846.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542823455820.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542823455820.png" new file mode 100644 index 00000000..bac0476d Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542823455820.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542823474720.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542823474720.png" new file mode 100644 index 00000000..47fd9f97 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542823474720.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542823505559.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542823505559.png" new file mode 100644 index 00000000..31f5cc5a Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542823505559.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542823539428.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542823539428.png" new file mode 100644 index 00000000..18bb5f3d Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542823539428.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542823589390.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542823589390.png" new file mode 100644 index 00000000..cab68148 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542823589390.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542823632598.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542823632598.png" new file mode 100644 index 00000000..291e96f0 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542823632598.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542823895008.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542823895008.png" new file mode 100644 index 00000000..fdc8ceec Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542823895008.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542824091867.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542824091867.png" new file mode 100644 index 00000000..c42d2d37 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542824091867.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542824195602.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542824195602.png" new file mode 100644 index 00000000..14bc7950 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542824195602.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542824318155.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542824318155.png" new file mode 100644 index 00000000..95ae9fbb Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542824318155.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542824486343.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542824486343.png" new file mode 100644 index 00000000..8b566496 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542824486343.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542824497736.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542824497736.png" new file mode 100644 index 00000000..fc710b03 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542824497736.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542824918145.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542824918145.png" new file mode 100644 index 00000000..cac48ce0 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542824918145.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542825063804.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542825063804.png" new file mode 100644 index 00000000..eec1b745 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542825063804.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542825205225.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542825205225.png" new file mode 100644 index 00000000..57e69ab3 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542825205225.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542825237816.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542825237816.png" new file mode 100644 index 00000000..f15d1aa0 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542825237816.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542825575318.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542825575318.png" new file mode 100644 index 00000000..4931c3e3 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542825575318.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542825908870.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542825908870.png" new file mode 100644 index 00000000..54504b74 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542825908870.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542825965528.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542825965528.png" new file mode 100644 index 00000000..eac85eb0 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542825965528.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542826334834.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542826334834.png" new file mode 100644 index 00000000..e194c5e2 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542826334834.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542826461988.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542826461988.png" new file mode 100644 index 00000000..75fa4e5c Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542826461988.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542826471739.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542826471739.png" new file mode 100644 index 00000000..4dd45263 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542826471739.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542826475517.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542826475517.png" new file mode 100644 index 00000000..d33b1cab Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542826475517.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542826542007.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542826542007.png" new file mode 100644 index 00000000..6de42035 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542826542007.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542826743056.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542826743056.png" new file mode 100644 index 00000000..da46997e Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542826743056.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542826809443.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542826809443.png" new file mode 100644 index 00000000..566f7484 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542826809443.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542826826991.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542826826991.png" new file mode 100644 index 00000000..a9adf76a Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542826826991.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542827203409.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542827203409.png" new file mode 100644 index 00000000..8b91b645 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542827203409.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542828076050.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542828076050.png" new file mode 100644 index 00000000..721617a2 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542828076050.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542828185735.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542828185735.png" new file mode 100644 index 00000000..53614a13 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542828185735.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542828483223.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542828483223.png" new file mode 100644 index 00000000..4b98113f Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1542828483223.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1cb62df2f6209e4c20fe5592dcc62918.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1cb62df2f6209e4c20fe5592dcc62918.jpg" new file mode 100644 index 00000000..8e1ff084 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1cb62df2f6209e4c20fe5592dcc62918.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1dffeb6986cf18354dafed0e1c08e09f.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1dffeb6986cf18354dafed0e1c08e09f.jpg" new file mode 100644 index 00000000..e27cb2bb Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._1dffeb6986cf18354dafed0e1c08e09f.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._20c3e041d5f5fdd3eceec976060c8b89.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._20c3e041d5f5fdd3eceec976060c8b89.jpg" new file mode 100644 index 00000000..18c85f4a Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._20c3e041d5f5fdd3eceec976060c8b89.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._2c8363bdbb6739578197ca68d05d362c.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._2c8363bdbb6739578197ca68d05d362c.jpg" new file mode 100644 index 00000000..10b82b31 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._2c8363bdbb6739578197ca68d05d362c.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._3d0802d34834b3aa3a8290fc194bc5be.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._3d0802d34834b3aa3a8290fc194bc5be.jpg" new file mode 100644 index 00000000..1c56351c Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._3d0802d34834b3aa3a8290fc194bc5be.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._3ea390bee08e90a87c4990322469592e.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._3ea390bee08e90a87c4990322469592e.jpg" new file mode 100644 index 00000000..124a0b9b Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._3ea390bee08e90a87c4990322469592e.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._40f2c27caa934c2d220d1d43ba0cef51.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._40f2c27caa934c2d220d1d43ba0cef51.jpg" new file mode 100644 index 00000000..f7abdd8c Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._40f2c27caa934c2d220d1d43ba0cef51.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._42d0f131b458659a0e642a3d0a156b09.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._42d0f131b458659a0e642a3d0a156b09.jpg" new file mode 100644 index 00000000..ab4d83a7 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._42d0f131b458659a0e642a3d0a156b09.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._4761dc00b96100769281e7c90011d09b.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._4761dc00b96100769281e7c90011d09b.jpg" new file mode 100644 index 00000000..73c55fc3 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._4761dc00b96100769281e7c90011d09b.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._4abacd82901988c3e0a98bdb07b2abc6.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._4abacd82901988c3e0a98bdb07b2abc6.jpg" new file mode 100644 index 00000000..31166ae9 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._4abacd82901988c3e0a98bdb07b2abc6.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._4f913ade7e7a16426fd809f6ac0af7b2.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._4f913ade7e7a16426fd809f6ac0af7b2.jpg" new file mode 100644 index 00000000..33b97d88 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._4f913ade7e7a16426fd809f6ac0af7b2.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._52de242e850347b9f0b7a7ad8dfa84b0.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._52de242e850347b9f0b7a7ad8dfa84b0.jpg" new file mode 100644 index 00000000..d5d4dd9f Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._52de242e850347b9f0b7a7ad8dfa84b0.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._5dc622ed6ec524048bee9be3da965903.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._5dc622ed6ec524048bee9be3da965903.jpg" new file mode 100644 index 00000000..23902dd5 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._5dc622ed6ec524048bee9be3da965903.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._5de65e5b7d2026c108b653d3ea60ffc2.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._5de65e5b7d2026c108b653d3ea60ffc2.jpg" new file mode 100644 index 00000000..43f1fd12 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._5de65e5b7d2026c108b653d3ea60ffc2.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._602723a1d3ce0f3abe7c591a8e4bb6ec.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._602723a1d3ce0f3abe7c591a8e4bb6ec.jpg" new file mode 100644 index 00000000..f47a910a Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._602723a1d3ce0f3abe7c591a8e4bb6ec.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._631e5aab4e0680c374793804817bfbb6.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._631e5aab4e0680c374793804817bfbb6.jpg" new file mode 100644 index 00000000..e37780d2 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._631e5aab4e0680c374793804817bfbb6.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._65162f4b973a249a4f9788b2af998bdb.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._65162f4b973a249a4f9788b2af998bdb.jpg" new file mode 100644 index 00000000..5157cdba Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._65162f4b973a249a4f9788b2af998bdb.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._693ac94b61c21e30e846aa9ecfb1883c.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._693ac94b61c21e30e846aa9ecfb1883c.jpg" new file mode 100644 index 00000000..01434835 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._693ac94b61c21e30e846aa9ecfb1883c.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._6fe355b691b487cc87f5ba4afd2dda3d.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._6fe355b691b487cc87f5ba4afd2dda3d.jpg" new file mode 100644 index 00000000..2e1d3459 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._6fe355b691b487cc87f5ba4afd2dda3d.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._71fcf4fee7500478ada89e52d72dcda1.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._71fcf4fee7500478ada89e52d72dcda1.jpg" new file mode 100644 index 00000000..e04a54ff Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._71fcf4fee7500478ada89e52d72dcda1.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._7caec88931b25c3a023021bccab48ae3.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._7caec88931b25c3a023021bccab48ae3.jpg" new file mode 100644 index 00000000..a5606927 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._7caec88931b25c3a023021bccab48ae3.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._857c3d2e84a6e9d5d31965252bcc9202.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._857c3d2e84a6e9d5d31965252bcc9202.jpg" new file mode 100644 index 00000000..c5984924 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._857c3d2e84a6e9d5d31965252bcc9202.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._8d017ade0d332c15d1a242a61fd447ec.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._8d017ade0d332c15d1a242a61fd447ec.jpg" new file mode 100644 index 00000000..ba5ef644 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._8d017ade0d332c15d1a242a61fd447ec.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._8d428fc8967ec734bd394cacfbfba40f.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._8d428fc8967ec734bd394cacfbfba40f.jpg" new file mode 100644 index 00000000..0549d13a Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._8d428fc8967ec734bd394cacfbfba40f.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._93f17238115b84db66ab5d56cfddacdd.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._93f17238115b84db66ab5d56cfddacdd.jpg" new file mode 100644 index 00000000..19fb130c Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._93f17238115b84db66ab5d56cfddacdd.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._966b912ade32d8171f18d2ea79b91b04.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._966b912ade32d8171f18d2ea79b91b04.jpg" new file mode 100644 index 00000000..96612011 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._966b912ade32d8171f18d2ea79b91b04.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._9898eb379bf1d726962b5928cfed69b0.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._9898eb379bf1d726962b5928cfed69b0.jpg" new file mode 100644 index 00000000..6930eca0 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._9898eb379bf1d726962b5928cfed69b0.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._a1122fb92521b6d3c484d264560473dc.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._a1122fb92521b6d3c484d264560473dc.jpg" new file mode 100644 index 00000000..88728787 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._a1122fb92521b6d3c484d264560473dc.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._a2a7e5cc9e4325b6f23d79efec9c51da.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._a2a7e5cc9e4325b6f23d79efec9c51da.jpg" new file mode 100644 index 00000000..8f8273cd Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._a2a7e5cc9e4325b6f23d79efec9c51da.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._a3db84158d9b6454adff88dbe4fa5d28.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._a3db84158d9b6454adff88dbe4fa5d28.jpg" new file mode 100644 index 00000000..6c6b55a1 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._a3db84158d9b6454adff88dbe4fa5d28.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._a814da5329927aca7b2a02cefb2e3f44.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._a814da5329927aca7b2a02cefb2e3f44.jpg" new file mode 100644 index 00000000..eb7aa306 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._a814da5329927aca7b2a02cefb2e3f44.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._aa10d36f758430dd4ff72d2bf6a76a6c.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._aa10d36f758430dd4ff72d2bf6a76a6c.jpg" new file mode 100644 index 00000000..5104b7bb Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._aa10d36f758430dd4ff72d2bf6a76a6c.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._ab78b954fa6c763bdc99072fb5a1f670.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._ab78b954fa6c763bdc99072fb5a1f670.jpg" new file mode 100644 index 00000000..358998f1 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._ab78b954fa6c763bdc99072fb5a1f670.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._ad24cbd2e510f912a72a82a2acfe92de.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._ad24cbd2e510f912a72a82a2acfe92de.jpg" new file mode 100644 index 00000000..ba6cfa51 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._ad24cbd2e510f912a72a82a2acfe92de.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._b1630ca5d004d4b430672c8b8ce7fb90.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._b1630ca5d004d4b430672c8b8ce7fb90.jpg" new file mode 100644 index 00000000..001ecd33 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._b1630ca5d004d4b430672c8b8ce7fb90.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._b4513fe8c46d8e429d9f5526fd66c57a.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._b4513fe8c46d8e429d9f5526fd66c57a.jpg" new file mode 100644 index 00000000..16fa3d54 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._b4513fe8c46d8e429d9f5526fd66c57a.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._c8e12bd34619cf9e3111be3e728b3aa6.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._c8e12bd34619cf9e3111be3e728b3aa6.jpg" new file mode 100644 index 00000000..e44a25c3 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._c8e12bd34619cf9e3111be3e728b3aa6.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._cf52633ba21fdb92e33853b80eb07ee0.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._cf52633ba21fdb92e33853b80eb07ee0.jpg" new file mode 100644 index 00000000..35e0c94a Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._cf52633ba21fdb92e33853b80eb07ee0.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._d8427680025580b726d99b1143bffd94.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._d8427680025580b726d99b1143bffd94.jpg" new file mode 100644 index 00000000..de2b336e Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._d8427680025580b726d99b1143bffd94.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._dd15dfa395f495d41806595f58f3754d.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._dd15dfa395f495d41806595f58f3754d.jpg" new file mode 100644 index 00000000..06dc04e7 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._dd15dfa395f495d41806595f58f3754d.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._e654d14df0b44ee4e8a0e505c654044b.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._e654d14df0b44ee4e8a0e505c654044b.jpg" new file mode 100644 index 00000000..690a16aa Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._e654d14df0b44ee4e8a0e505c654044b.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._f0cccba910e0833cb8455d4fe84a7dc8.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._f0cccba910e0833cb8455d4fe84a7dc8.jpg" new file mode 100644 index 00000000..04874776 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._f0cccba910e0833cb8455d4fe84a7dc8.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._f852afecfb647f6b2727c4dcbabb1323.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._f852afecfb647f6b2727c4dcbabb1323.jpg" new file mode 100644 index 00000000..751c6809 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._f852afecfb647f6b2727c4dcbabb1323.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._fa08900e89bfd53cc28345d21bc6aca0.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._fa08900e89bfd53cc28345d21bc6aca0.jpg" new file mode 100644 index 00000000..f9f10767 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._fa08900e89bfd53cc28345d21bc6aca0.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._fa99e7c6f1985ddc380d04d4eb3adf26.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._fa99e7c6f1985ddc380d04d4eb3adf26.jpg" new file mode 100644 index 00000000..74fe37f5 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._fa99e7c6f1985ddc380d04d4eb3adf26.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._fcbe02803e45f6455a4602b645b472c5.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._fcbe02803e45f6455a4602b645b472c5.jpg" new file mode 100644 index 00000000..7206b940 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._fcbe02803e45f6455a4602b645b472c5.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._fed8fcb90eedfa6d3c4b11464c3440cb.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._fed8fcb90eedfa6d3c4b11464c3440cb.jpg" new file mode 100644 index 00000000..a9382f17 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._fed8fcb90eedfa6d3c4b11464c3440cb.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._ffdf5ed6d284f09e2f3c8d3e062c9bc2.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._ffdf5ed6d284f09e2f3c8d3e062c9bc2.jpg" new file mode 100644 index 00000000..38b8e661 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/__MACOSX/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/._ffdf5ed6d284f09e2f3c8d3e062c9bc2.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11.pdf" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11.pdf" new file mode 100644 index 00000000..d6805efc Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11.pdf" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/img/ch11/1542972502781.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/img/ch11/1542972502781.png" similarity index 100% rename from "ch11_\350\277\201\347\247\273\345\255\246\344\271\240/img/ch11/1542972502781.png" rename to "ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/img/ch11/1542972502781.png" diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/img/ch11/1542973960796.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/img/ch11/1542973960796.png" similarity index 100% rename from "ch11_\350\277\201\347\247\273\345\255\246\344\271\240/img/ch11/1542973960796.png" rename to "ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/img/ch11/1542973960796.png" diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/img/ch11/1542974131814.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/img/ch11/1542974131814.png" similarity index 100% rename from "ch11_\350\277\201\347\247\273\345\255\246\344\271\240/img/ch11/1542974131814.png" rename to "ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/img/ch11/1542974131814.png" diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/img/ch11/readme.md" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/img/ch11/readme.md" similarity index 100% rename from "ch11_\350\277\201\347\247\273\345\255\246\344\271\240/img/ch11/readme.md" rename to "ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/img/ch11/readme.md" diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/00864b9c79b810761fec244e89a0ea08.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/00864b9c79b810761fec244e89a0ea08.jpg" new file mode 100644 index 00000000..cf8a5121 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/00864b9c79b810761fec244e89a0ea08.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/02cf7802ec9aabdccf710442cda04ccb.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/02cf7802ec9aabdccf710442cda04ccb.jpg" new file mode 100644 index 00000000..b018e177 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/02cf7802ec9aabdccf710442cda04ccb.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/07e7da7afdea5c38f470b3a06d8137e2.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/07e7da7afdea5c38f470b3a06d8137e2.jpg" new file mode 100644 index 00000000..8e6c2809 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/07e7da7afdea5c38f470b3a06d8137e2.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/0854b7278c50c5e2b0bbe61d273721c1.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/0854b7278c50c5e2b0bbe61d273721c1.jpg" new file mode 100644 index 00000000..d34a3df7 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/0854b7278c50c5e2b0bbe61d273721c1.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/09cb64cf3f3ceb5d87369e41c29d34bf.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/09cb64cf3f3ceb5d87369e41c29d34bf.jpg" new file mode 100644 index 00000000..7861d49b Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/09cb64cf3f3ceb5d87369e41c29d34bf.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/0b5d1ded61af9b38fedb2746a7dda23e.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/0b5d1ded61af9b38fedb2746a7dda23e.jpg" new file mode 100644 index 00000000..e2dbeb68 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/0b5d1ded61af9b38fedb2746a7dda23e.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/0f3a57ffdefd178a4db06b52c2d53b58.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/0f3a57ffdefd178a4db06b52c2d53b58.jpg" new file mode 100644 index 00000000..d4d7cb59 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/0f3a57ffdefd178a4db06b52c2d53b58.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/103de3658cbb97ad4c24bafe28f9d957.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/103de3658cbb97ad4c24bafe28f9d957.jpg" new file mode 100644 index 00000000..6f940fa1 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/103de3658cbb97ad4c24bafe28f9d957.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542808441403.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542808441403.png" new file mode 100644 index 00000000..ad0a0408 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542808441403.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542812321831.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542812321831.png" new file mode 100644 index 00000000..c620942f Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542812321831.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542812440636.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542812440636.png" new file mode 100644 index 00000000..c620942f Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542812440636.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542812748062.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542812748062.png" new file mode 100644 index 00000000..e9d4896c Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542812748062.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542817257337.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542817257337.png" new file mode 100644 index 00000000..47ca18f5 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542817257337.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542817481582.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542817481582.png" new file mode 100644 index 00000000..cd1ff206 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542817481582.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542820738631.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542820738631.png" new file mode 100644 index 00000000..96b03027 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542820738631.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542820752570.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542820752570.png" new file mode 100644 index 00000000..65ed0664 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542820752570.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542820774326.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542820774326.png" new file mode 100644 index 00000000..01864641 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542820774326.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542820797637.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542820797637.png" new file mode 100644 index 00000000..8e378853 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542820797637.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542821989163.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542821989163.png" new file mode 100644 index 00000000..46899e4c Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542821989163.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542822045307.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542822045307.png" new file mode 100644 index 00000000..cea8d2a1 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542822045307.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542822087844.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542822087844.png" new file mode 100644 index 00000000..168bdd04 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542822087844.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542822226596.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542822226596.png" new file mode 100644 index 00000000..27ccbdce Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542822226596.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542822305161.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542822305161.png" new file mode 100644 index 00000000..659e86f6 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542822305161.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542822326035.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542822326035.png" new file mode 100644 index 00000000..7d0e2ef0 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542822326035.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542822355361.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542822355361.png" new file mode 100644 index 00000000..7d0e2ef0 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542822355361.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542822398717.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542822398717.png" new file mode 100644 index 00000000..c5282076 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542822398717.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542822474045.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542822474045.png" new file mode 100644 index 00000000..c064b44c Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542822474045.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542822558549.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542822558549.png" new file mode 100644 index 00000000..7f64fbb2 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542822558549.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542822578502.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542822578502.png" new file mode 100644 index 00000000..fbfa2d82 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542822578502.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542822851294.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542822851294.png" new file mode 100644 index 00000000..36f573b1 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542822851294.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542822971212.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542822971212.png" new file mode 100644 index 00000000..62d24a6a Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542822971212.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542823019007.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542823019007.png" new file mode 100644 index 00000000..14cf119d Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542823019007.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542823210556.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542823210556.png" new file mode 100644 index 00000000..986273c6 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542823210556.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542823438846.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542823438846.png" new file mode 100644 index 00000000..a3c4dbc3 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542823438846.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542823455820.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542823455820.png" new file mode 100644 index 00000000..7cfd51d9 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542823455820.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542823474720.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542823474720.png" new file mode 100644 index 00000000..08be3ab2 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542823474720.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542823505559.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542823505559.png" new file mode 100644 index 00000000..82e1d52e Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542823505559.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542823539428.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542823539428.png" new file mode 100644 index 00000000..65e6e43c Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542823539428.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542823589390.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542823589390.png" new file mode 100644 index 00000000..e238a80e Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542823589390.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542823632598.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542823632598.png" new file mode 100644 index 00000000..fda1ec56 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542823632598.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542823895008.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542823895008.png" new file mode 100644 index 00000000..12b72750 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542823895008.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542824091867.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542824091867.png" new file mode 100644 index 00000000..0657cb71 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542824091867.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542824195602.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542824195602.png" new file mode 100644 index 00000000..9c60006d Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542824195602.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542824318155.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542824318155.png" new file mode 100644 index 00000000..5d7ce48e Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542824318155.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542824486343.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542824486343.png" new file mode 100644 index 00000000..54c6c93b Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542824486343.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542824497736.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542824497736.png" new file mode 100644 index 00000000..9e385670 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542824497736.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542824918145.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542824918145.png" new file mode 100644 index 00000000..149a39d6 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542824918145.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542825063804.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542825063804.png" new file mode 100644 index 00000000..106d7143 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542825063804.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542825205225.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542825205225.png" new file mode 100644 index 00000000..ce1afcb0 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542825205225.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542825237816.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542825237816.png" new file mode 100644 index 00000000..cff94112 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542825237816.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542825575318.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542825575318.png" new file mode 100644 index 00000000..93424754 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542825575318.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542825908870.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542825908870.png" new file mode 100644 index 00000000..1e7e9057 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542825908870.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542825965528.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542825965528.png" new file mode 100644 index 00000000..b98512b8 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542825965528.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542826334834.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542826334834.png" new file mode 100644 index 00000000..db11e5a6 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542826334834.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542826461988.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542826461988.png" new file mode 100644 index 00000000..ba7d28b3 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542826461988.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542826471739.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542826471739.png" new file mode 100644 index 00000000..208995f0 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542826471739.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542826475517.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542826475517.png" new file mode 100644 index 00000000..208995f0 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542826475517.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542826542007.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542826542007.png" new file mode 100644 index 00000000..497b79f6 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542826542007.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542826743056.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542826743056.png" new file mode 100644 index 00000000..1d0602a3 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542826743056.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542826809443.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542826809443.png" new file mode 100644 index 00000000..87c80588 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542826809443.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542826826991.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542826826991.png" new file mode 100644 index 00000000..44eb01be Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542826826991.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542827203409.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542827203409.png" new file mode 100644 index 00000000..21240915 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542827203409.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542828076050.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542828076050.png" new file mode 100644 index 00000000..0cb0dd01 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542828076050.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542828185735.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542828185735.png" new file mode 100644 index 00000000..daee5556 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542828185735.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542828483223.png" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542828483223.png" new file mode 100644 index 00000000..daee5556 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1542828483223.png" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1cb62df2f6209e4c20fe5592dcc62918.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1cb62df2f6209e4c20fe5592dcc62918.jpg" new file mode 100644 index 00000000..58e52518 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1cb62df2f6209e4c20fe5592dcc62918.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1dffeb6986cf18354dafed0e1c08e09f.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1dffeb6986cf18354dafed0e1c08e09f.jpg" new file mode 100644 index 00000000..4fcc13d2 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/1dffeb6986cf18354dafed0e1c08e09f.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/20c3e041d5f5fdd3eceec976060c8b89.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/20c3e041d5f5fdd3eceec976060c8b89.jpg" new file mode 100644 index 00000000..ae460d6e Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/20c3e041d5f5fdd3eceec976060c8b89.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/2c8363bdbb6739578197ca68d05d362c.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/2c8363bdbb6739578197ca68d05d362c.jpg" new file mode 100644 index 00000000..26483989 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/2c8363bdbb6739578197ca68d05d362c.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/3d0802d34834b3aa3a8290fc194bc5be.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/3d0802d34834b3aa3a8290fc194bc5be.jpg" new file mode 100644 index 00000000..d1b06822 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/3d0802d34834b3aa3a8290fc194bc5be.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/3ea390bee08e90a87c4990322469592e.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/3ea390bee08e90a87c4990322469592e.jpg" new file mode 100644 index 00000000..f4d1d73c Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/3ea390bee08e90a87c4990322469592e.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/40f2c27caa934c2d220d1d43ba0cef51.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/40f2c27caa934c2d220d1d43ba0cef51.jpg" new file mode 100644 index 00000000..38ca9dec Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/40f2c27caa934c2d220d1d43ba0cef51.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/42d0f131b458659a0e642a3d0a156b09.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/42d0f131b458659a0e642a3d0a156b09.jpg" new file mode 100644 index 00000000..cbb91921 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/42d0f131b458659a0e642a3d0a156b09.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/4761dc00b96100769281e7c90011d09b.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/4761dc00b96100769281e7c90011d09b.jpg" new file mode 100644 index 00000000..9047608c Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/4761dc00b96100769281e7c90011d09b.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/4abacd82901988c3e0a98bdb07b2abc6.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/4abacd82901988c3e0a98bdb07b2abc6.jpg" new file mode 100644 index 00000000..f3104a66 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/4abacd82901988c3e0a98bdb07b2abc6.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/4f913ade7e7a16426fd809f6ac0af7b2.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/4f913ade7e7a16426fd809f6ac0af7b2.jpg" new file mode 100644 index 00000000..71f5203d Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/4f913ade7e7a16426fd809f6ac0af7b2.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/52de242e850347b9f0b7a7ad8dfa84b0.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/52de242e850347b9f0b7a7ad8dfa84b0.jpg" new file mode 100644 index 00000000..61ae000b Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/52de242e850347b9f0b7a7ad8dfa84b0.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/5dc622ed6ec524048bee9be3da965903.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/5dc622ed6ec524048bee9be3da965903.jpg" new file mode 100644 index 00000000..98d80ab5 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/5dc622ed6ec524048bee9be3da965903.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/5de65e5b7d2026c108b653d3ea60ffc2.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/5de65e5b7d2026c108b653d3ea60ffc2.jpg" new file mode 100644 index 00000000..bde80b63 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/5de65e5b7d2026c108b653d3ea60ffc2.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/602723a1d3ce0f3abe7c591a8e4bb6ec.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/602723a1d3ce0f3abe7c591a8e4bb6ec.jpg" new file mode 100644 index 00000000..1161226d Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/602723a1d3ce0f3abe7c591a8e4bb6ec.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/631e5aab4e0680c374793804817bfbb6.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/631e5aab4e0680c374793804817bfbb6.jpg" new file mode 100644 index 00000000..516278d1 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/631e5aab4e0680c374793804817bfbb6.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/65162f4b973a249a4f9788b2af998bdb.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/65162f4b973a249a4f9788b2af998bdb.jpg" new file mode 100644 index 00000000..91ab5bd4 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/65162f4b973a249a4f9788b2af998bdb.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/693ac94b61c21e30e846aa9ecfb1883c.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/693ac94b61c21e30e846aa9ecfb1883c.jpg" new file mode 100644 index 00000000..0d593a5c Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/693ac94b61c21e30e846aa9ecfb1883c.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/6fe355b691b487cc87f5ba4afd2dda3d.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/6fe355b691b487cc87f5ba4afd2dda3d.jpg" new file mode 100644 index 00000000..db3c3f05 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/6fe355b691b487cc87f5ba4afd2dda3d.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/71fcf4fee7500478ada89e52d72dcda1.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/71fcf4fee7500478ada89e52d72dcda1.jpg" new file mode 100644 index 00000000..ae0f2cba Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/71fcf4fee7500478ada89e52d72dcda1.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/7caec88931b25c3a023021bccab48ae3.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/7caec88931b25c3a023021bccab48ae3.jpg" new file mode 100644 index 00000000..6b1de455 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/7caec88931b25c3a023021bccab48ae3.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/857c3d2e84a6e9d5d31965252bcc9202.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/857c3d2e84a6e9d5d31965252bcc9202.jpg" new file mode 100644 index 00000000..67ff11da Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/857c3d2e84a6e9d5d31965252bcc9202.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/8d017ade0d332c15d1a242a61fd447ec.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/8d017ade0d332c15d1a242a61fd447ec.jpg" new file mode 100644 index 00000000..2d4b3d20 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/8d017ade0d332c15d1a242a61fd447ec.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/8d428fc8967ec734bd394cacfbfba40f.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/8d428fc8967ec734bd394cacfbfba40f.jpg" new file mode 100644 index 00000000..06921fc4 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/8d428fc8967ec734bd394cacfbfba40f.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/93f17238115b84db66ab5d56cfddacdd.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/93f17238115b84db66ab5d56cfddacdd.jpg" new file mode 100644 index 00000000..7359dfc0 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/93f17238115b84db66ab5d56cfddacdd.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/966b912ade32d8171f18d2ea79b91b04.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/966b912ade32d8171f18d2ea79b91b04.jpg" new file mode 100644 index 00000000..ab01cce6 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/966b912ade32d8171f18d2ea79b91b04.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/9898eb379bf1d726962b5928cfed69b0.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/9898eb379bf1d726962b5928cfed69b0.jpg" new file mode 100644 index 00000000..0a387aa6 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/9898eb379bf1d726962b5928cfed69b0.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/a1122fb92521b6d3c484d264560473dc.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/a1122fb92521b6d3c484d264560473dc.jpg" new file mode 100644 index 00000000..ee85f853 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/a1122fb92521b6d3c484d264560473dc.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/a2a7e5cc9e4325b6f23d79efec9c51da.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/a2a7e5cc9e4325b6f23d79efec9c51da.jpg" new file mode 100644 index 00000000..ff871c14 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/a2a7e5cc9e4325b6f23d79efec9c51da.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/a3db84158d9b6454adff88dbe4fa5d28.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/a3db84158d9b6454adff88dbe4fa5d28.jpg" new file mode 100644 index 00000000..b074b8f6 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/a3db84158d9b6454adff88dbe4fa5d28.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/a814da5329927aca7b2a02cefb2e3f44.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/a814da5329927aca7b2a02cefb2e3f44.jpg" new file mode 100644 index 00000000..a8346126 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/a814da5329927aca7b2a02cefb2e3f44.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/aa10d36f758430dd4ff72d2bf6a76a6c.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/aa10d36f758430dd4ff72d2bf6a76a6c.jpg" new file mode 100644 index 00000000..c4dec113 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/aa10d36f758430dd4ff72d2bf6a76a6c.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/ab78b954fa6c763bdc99072fb5a1f670.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/ab78b954fa6c763bdc99072fb5a1f670.jpg" new file mode 100644 index 00000000..32fb745d Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/ab78b954fa6c763bdc99072fb5a1f670.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/ad24cbd2e510f912a72a82a2acfe92de.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/ad24cbd2e510f912a72a82a2acfe92de.jpg" new file mode 100644 index 00000000..b7388092 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/ad24cbd2e510f912a72a82a2acfe92de.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/b1630ca5d004d4b430672c8b8ce7fb90.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/b1630ca5d004d4b430672c8b8ce7fb90.jpg" new file mode 100644 index 00000000..c888b75e Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/b1630ca5d004d4b430672c8b8ce7fb90.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/b4513fe8c46d8e429d9f5526fd66c57a.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/b4513fe8c46d8e429d9f5526fd66c57a.jpg" new file mode 100644 index 00000000..d01eaf04 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/b4513fe8c46d8e429d9f5526fd66c57a.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/c8e12bd34619cf9e3111be3e728b3aa6.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/c8e12bd34619cf9e3111be3e728b3aa6.jpg" new file mode 100644 index 00000000..90d544db Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/c8e12bd34619cf9e3111be3e728b3aa6.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/cf52633ba21fdb92e33853b80eb07ee0.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/cf52633ba21fdb92e33853b80eb07ee0.jpg" new file mode 100644 index 00000000..73f3449b Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/cf52633ba21fdb92e33853b80eb07ee0.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/d8427680025580b726d99b1143bffd94.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/d8427680025580b726d99b1143bffd94.jpg" new file mode 100644 index 00000000..ca87e066 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/d8427680025580b726d99b1143bffd94.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/dd15dfa395f495d41806595f58f3754d.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/dd15dfa395f495d41806595f58f3754d.jpg" new file mode 100644 index 00000000..cb796618 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/dd15dfa395f495d41806595f58f3754d.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/e654d14df0b44ee4e8a0e505c654044b.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/e654d14df0b44ee4e8a0e505c654044b.jpg" new file mode 100644 index 00000000..aae50871 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/e654d14df0b44ee4e8a0e505c654044b.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/f0cccba910e0833cb8455d4fe84a7dc8.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/f0cccba910e0833cb8455d4fe84a7dc8.jpg" new file mode 100644 index 00000000..60008837 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/f0cccba910e0833cb8455d4fe84a7dc8.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/f852afecfb647f6b2727c4dcbabb1323.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/f852afecfb647f6b2727c4dcbabb1323.jpg" new file mode 100644 index 00000000..c0894f84 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/f852afecfb647f6b2727c4dcbabb1323.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/fa08900e89bfd53cc28345d21bc6aca0.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/fa08900e89bfd53cc28345d21bc6aca0.jpg" new file mode 100644 index 00000000..aaeabf7e Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/fa08900e89bfd53cc28345d21bc6aca0.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/fa99e7c6f1985ddc380d04d4eb3adf26.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/fa99e7c6f1985ddc380d04d4eb3adf26.jpg" new file mode 100644 index 00000000..e12d19c4 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/fa99e7c6f1985ddc380d04d4eb3adf26.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/fcbe02803e45f6455a4602b645b472c5.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/fcbe02803e45f6455a4602b645b472c5.jpg" new file mode 100644 index 00000000..1772f912 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/fcbe02803e45f6455a4602b645b472c5.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/fed8fcb90eedfa6d3c4b11464c3440cb.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/fed8fcb90eedfa6d3c4b11464c3440cb.jpg" new file mode 100644 index 00000000..59eca95b Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/fed8fcb90eedfa6d3c4b11464c3440cb.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/ffdf5ed6d284f09e2f3c8d3e062c9bc2.jpg" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/ffdf5ed6d284f09e2f3c8d3e062c9bc2.jpg" new file mode 100644 index 00000000..9206f709 Binary files /dev/null and "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/media/ffdf5ed6d284f09e2f3c8d3e062c9bc2.jpg" differ diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/\347\254\254\345\215\201\344\270\200\347\253\240_\350\277\201\347\247\273\345\255\246\344\271\240.md" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/\347\254\254\345\215\201\344\270\200\347\253\240_\350\277\201\347\247\273\345\255\246\344\271\240.md" new file mode 100644 index 00000000..8dd9016f --- /dev/null +++ "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/\347\254\254\345\215\201\344\270\200\347\253\240_\350\277\201\347\247\273\345\255\246\344\271\240.md" @@ -0,0 +1,671 @@ +[TOC] + +# 第十一章 迁移学习 +​ 本章主要简明地介绍了迁移学习的基本概念、迁移学习的必要性、研究领域和基本方法。重点介绍了几大类常用的迁移学习方法:数据分布自适应方法、特征选择方法、子空间学习方法、以及目前最热门的深度迁移学习方法。除此之外,我们也结合最近的一些研究成果对未来迁移学习进行了一些展望。并提供了一些迁移学习领域的常用学习资源,以方便感兴趣的读者快速开始学习。 + +## 11.1 迁移学习基础知识 + +### 11.1.1 什么是迁移学习? + +找到目标问题的相似性,迁移学习任务就是从相似性出发,将旧领域(domain)学习过的模型应用在新领域上。 + +### 11.1.2 为什么需要迁移学习? + +1. **大数据与少标注的矛盾**:虽然有大量的数据,但往往都是没有标注的,无法训练机器学习模型。人工进行数据标定太耗时。 +2. **大数据与弱计算的矛盾**:普通人无法拥有庞大的数据量与计算资源。因此需要借助于模型的迁移。 +3. **普适化模型与个性化需求的矛盾**:即使是在同一个任务上,一个模型也往往难以满足每个人的个性化需求,比如特定的隐私设置。这就需要在不同人之间做模型的适配。 +4. **特定应用(如冷启动)的需求**。 + +### 11.1.3 迁移学习的基本问题有哪些? + +基本问题主要有3个: + +- **How to transfer**: 如何进行迁移学习?(设计迁移方法) +- **What to transfer**: 给定一个目标领域,如何找到相对应的源领域,然后进行迁移?(源领域选择) +- **When to transfer**: 什么时候可以进行迁移,什么时候不可以?(避免负迁移) + +### 11.1.4 迁移学习有哪些常用概念? + +- 基本定义 + - **域(Domain)**:数据特征和特征分布组成,是学习的主体 + - **源域 (Source domain)**:已有知识的域 + - **目标域 (Target domain)**:要进行学习的域 + - **任务 (Task)**:由目标函数和学习结果组成,是学习的结果 +- 按特征空间分类 + - **同构迁移学习(Homogeneous TL)**: 源域和目标域的特征空间相同,$D_s=D_t$ + - **异构迁移学习(Heterogeneous TL)**:源域和目标域的特征空间不同,$D_s\ne D_t$ +- 按迁移情景分类 + - **归纳式迁移学习(Inductive TL)**:源域和目标域的学习任务不同 + - **直推式迁移学习(Transductive TL)**:源域和目标域不同,学习任务相同 + - **无监督迁移学习(Unsupervised TL)**:源域和目标域均没有标签 +- 按迁移方法分类 + - **基于实例的迁移 (Instance based TL)**:通过权重重用源域和目标域的样例进行迁移 + - **基于特征的迁移 (Feature based TL)**:将源域和目标域的特征变换到相同空间 + - **基于模型的迁移 (Parameter based TL)**:利用源域和目标域的参数共享模型 + - **基于关系的迁移 (Relation based TL)**:利用源域中的逻辑网络关系进行迁移 + +![1542972502781](./img/ch11/1542972502781.png) + +![1542974131814](./img/ch11/1542974131814.png) + +### 11.1.5 迁移学习与传统机器学习有什么区别? + +| | 迁移学习 | 传统机器学习 | +| -------- | -------------------------- | -------------------- | +| 数据分布 | 训练和测试数据不需要同分布 | 训练和测试数据同分布 | +| 数据标签 | 不需要足够的数据标注 | 足够的数据标注 | +| 建模 | 可以重用之前的模型 | 每个任务分别建模 | + +![1542973960796](./img/ch11/1542973960796.png) +### 11.1.6 迁移学习的核心及度量准则? + +**迁移学习的总体思路可以概括为**:开发算法来最大限度地利用有标注的领域的知识,来辅助目标领域的知识获取和学习。 + +**迁移学习的核心是**:找到源领域和目标领域之间的相似性,并加以合理利用。这种相似性非常普遍。比如,不同人的身体构造是相似的;自行车和摩托车的骑行方式是相似的;国际象棋和中国象棋是相似的;羽毛球和网球的打球方式是相似的。这种相似性也可以理解为不变量。以不变应万变,才能立于不败之地。 + +**有了这种相似性后,下一步工作就是, 如何度量和利用这种相似性。**度量工作的目标有两点:一是很好地度量两个领域的相似性,不仅定性地告诉我们它们是否相似,更定量地给出相似程度。二是以度量为准则,通过我们所要采用的学习手段,增大两个领域之间的相似性,从而完成迁移学习。 + +**一句话总结: 相似性是核心,度量准则是重要手段。** + +### 11.1.7 迁移学习与其他概念的区别? + +1. 迁移学习与多任务学习关系: + * **多任务学习**:多个相关任务一起协同学习; + * **迁移学习**:强调信息复用,从一个领域(domain)迁移到另一个领域。 +2. 迁移学习与领域自适应:**领域自适应**:使两个特征分布不一致的domain一致。 +3. 迁移学习与协方差漂移:**协方差漂移**:数据的条件概率分布发生变化。 + + +Reference: + +1. [王晋东,迁移学习简明手册](https://github.com/jindongwang/transferlearning-tutorial) +2. Ben-David, S., Blitzer, J., Crammer, K., Kulesza, A., Pereira, F., & Vaughan, J. W. (2010). A theory of learning from different domains. Machine learning, 79(1-2), 151-175. +3. Tan, B., Song, Y., Zhong, E. and Yang, Q., 2015, August. Transitive transfer learning. In Proceedings of the 21th ACM SIGKDD International Conference on Knowledge Discovery and Data Mining (pp. 1155-1164). ACM. + +### 11.1.8 什么是负迁移?产生负迁移的原因有哪些? +负迁移(Negative Transfer)指的是,在源域上学习到的知识,对于目标域上的学习产生负面作用。 + +产生负迁移的原因主要有: +- 数据问题:源域和目标域压根不相似,谈何迁移? +- 方法问题:源域和目标域是相似的,但是,迁移学习方法不够好,没找到可迁移的成分。 + +负迁移给迁移学习的研究和应用带来了负面影响。在实际应用中,找到合理的相似性,并且选择或开发合理的迁移学习方法,能够避免负迁移现象。 + +### 11.1.9 迁移学习的基本思路? + +迁移学习的总体思路可以概括为:开发算法来最大限度地利用有标注的领域的知识,来辅助目标领域的知识获取和学习。 + +1. 找到目标问题的相似性,迁移学习任务就是从相似性出发,将旧领域(domain)学习过的模型应用在新领域上。 +2. 迁移学习,是指利用数据、任务、或模型之间的相似性,将在旧领域学习过的模型,应用于新领域的一种学习过程。 +3. 迁移学习**最有用的场合**是,如果你尝试优化任务B的性能,通常这个任务数据相对较少。 + 例如,在放射科中你知道很难收集很多射线扫描图来搭建一个性能良好的放射科诊断系统,所以在这种情况下,你可能会找一个相关但不同的任务,如图像识别,其中你可能用 1 百万张图片训练过了,并从中学到很多低层次特征,所以那也许能帮助网络在任务在放射科任务上做得更好,尽管任务没有这么多数据。 +4. 迁移学习什么时候是有意义的?它确实可以**显著提高**你的**学习任务的性能**,但我有时候也见过有些场合使用迁移学习时,任务实际上数据量比任务要少, 这种情况下增益可能不多。 +> 什么情况下可以使用迁移学习? +> +> 假如两个领域之间的区别特别的大,**不可以直接采用迁移学习**,因为在这种情况下效果不是很好。在这种情况下,推荐使用[3]的工作,在两个相似度很低的domain之间一步步迁移过去(踩着石头过河)。 + +> 1. 迁移学习主要解决方案有哪些? +> 2. 除直接看infer的结果的Accurancy以外,如何衡量迁移学习学习效果? +> 3. 对抗网络是如何进行迁移的? + +Reference: + +1. [王晋东,迁移学习简明手册](https://github.com/jindongwang/transferlearning-tutorial) +2. Ben-David, S., Blitzer, J., Crammer, K., Kulesza, A., Pereira, F., & Vaughan, J. W. (2010). A theory of learning from different domains. Machine learning, 79(1-2), 151-175. +3. Tan, B., Song, Y., Zhong, E. and Yang, Q., 2015, August. Transitive transfer learning. In Proceedings of the 21th ACM SIGKDD International Conference on Knowledge Discovery and Data Mining (pp. 1155-1164). ACM. + + +### 11.1.10 迁移学习与传统机器学习有什么区别? + +| | 迁移学习 | 传统机器学习 | +| -------- | -------------------------- | -------------------- | +| 数据分布 | 训练和测试数据不需要同分布 | 训练和测试数据同分布 | +| 数据标签 | 不需要足够的数据标注 | 足够的数据标注 | +| 建模 | 可以重用之前的模型 | 每个任务分别建模 | + +![1542973960796](./img/ch11/1542973960796.png) + + + +## 11.2 迁移学习的基本思路有哪些? + +​ 迁移学习的基本方法可以分为四种。这四种基本的方法分别是:基于样本的迁移, 基于模型 的迁移, 基于特征的迁移,及基于关系的迁移。 + +### 11.2.1 基于样本迁移 + +​ 基于样本的迁移学习方法 (Instance based Transfer Learning) 根据一定的权重生成规则,对数据样本进行重用,来进行迁移学习。图[14](#bookmark90)形象地表示了基于样本迁移方法的思想源域中存在不同种类的动物,如狗、鸟、猫等,目标域只有狗这一种类别。在迁移时,为了最大限度地和目标域相似,我们可以人为地提高源域中属于狗这个类别的样本权重。 + +![](./media/631e5aab4e0680c374793804817bfbb6.jpg) + +
图 14: 基于样本的迁移学习方法示意图 + +​ 在迁移学习中,对于源域D~s~和目标域D~t~,通常假定产生它们的概率分布是不同且未知的(P(X~s~) =P(X~t~))。另外,由于实例的维度和数量通常都非常大,因此,直接对 P(X~s~) 和P(X~t~) 进行估计是不可行的。因而,大量的研究工作 [[Khan and Heisterkamp,2016](#bookmark267), [Zadrozny, 2004](#bookmark319), [Cortes et al.,2008](#bookmark242), [Dai et al., 2007](#bookmark243), [Tan et al.,2015](#bookmark302), [Tan et al., 2017](#bookmark303)] 着眼于对源域和目标域的分布比值进行估计(P(**X**t)/P(**X**s))。所估计得到的比值即为样本的权重。这些方法通常都假设P(**x**s) \<并且源域和目标域的条件概率分布相同(P(y\|x~s~)=*P*(y\|x~t~))。特别地,上海交通大学Dai等人[[Dai et al.,2007](#bookmark243)]提出了 TrAdaboost方法,将AdaBoost的思想应用于迁移学习中,提高有利于目标分类任务的实例权重、降低不利于目标分类任务的实例权重,并基于PAC理论推导了模型的泛化误差上界。TrAdaBoost方法是此方面的经典研究之一。文献 [[Huang et al., 2007](#bookmark264)]提出核均值匹配方法 (Kernel Mean atching, KMM)对于概率分布进行估计,目标是使得加权后的源域和目标域的概率分布尽可能相近。在最新的研究成果中,香港科技大学的Tan等人扩展了实例迁移学习方法的应用场景,提出 了传递迁移学习方法(Transitive Transfer Learning, TTL) [[Tan etal., 2015](#bookmark302)] 和远域迁移学习 (Distant Domain Transfer Learning,DDTL) [[Tan et al., 2017](#bookmark303)],利用联合矩阵分解和深度神经网络,将迁移学习应用于多个不相似的领域之间的知识共享,取得了良好的效果。 + +​ 虽然实例权重法具有较好的理论支撑、容易推导泛化误差上界,但这类方法通常只在领域间分布差异较小时有效,因此对自然语言处理、计算机视觉等任务效果并不理想。而基于特征表示的迁移学习方法效果更好,是我们研究的重点。 + +### 11.2.2 基于特征迁移 + +​ 基于特征的迁移方法 (Feature based Transfer Learning) 是指将通过特征变换的方式互相迁移 [[Liu et al., 2011](#bookmark272), [Zheng et al.,2008](#bookmark327), [Hu and Yang, 2011](#bookmark263)],来减少源域和目标域之间的差距;或者将源域和目标域的数据特征变换到统一特征空间中 [[Pan et al.,2011](#bookmark288), [Long et al., 2014b](#bookmark278), [Duan et al.,2012](#bookmark248)],然后利用传统的机器学习方法进行分类识别。根据特征的同构和异构性,又可以分为同构和异构迁移学习。图[15](#bookmark93)很形象地表示了两种基于特 征的迁移学习方法。 + +![](./media/fa08900e89bfd53cc28345d21bc6aca0.jpg) + +
图 15: 基于特征的迁移学习方法示意图 + +​ 基于特征的迁移学习方法是迁移学习领域中最热门的研究方法,这类方法通常假设源域和目标域间有一些交叉的特征。香港科技大学的 Pan 等人 [[Pan et al.,2011](#bookmark288)] 提出的迁移 成分分析方法 (Transfer Component Analysis, TCA)是其中较为典型的一个方法。该方法的 核心内容是以最大均值差异 (Maximum MeanDiscrepancy, MMD) [[Borgwardt et al., 2006](#bookmark236)]作为度量准则,将不同数据领域中的分布差异最小化。加州大学伯克利分校的 Blitzer 等人 [[Blitzer et al., 2006](#bookmark235)] 提出了一种基于结构对应的学习方法(Structural Corresponding Learning,SCL),该算法可以通过映射将一个空间中独有的一些特征变换到其他所有空间中的轴特征上,然后在该特征上使用机器学习的算法进行分类预测。清华大学龙明盛等人[[Long et al.,2014b](#bookmark278)]提出在最小化分布距离的同时,加入实例选择的迁移联合匹配(Tran-fer Joint Matching, TJM) 方法,将实例和特征迁移学习方法进行了有机的结合。澳大利亚卧龙岗大学的 Jing Zhang 等人 [[Zhang et al., 2017a](#bookmark321)]提出对于源域和目标域各自训练不同 的变换矩阵,从而达到迁移学习的目标。 + +### 11.2.3 基于模型迁移 + +​ 基于模型的迁移方法 (Parameter/Model based Transfer Learning) 是指从源域和目标域中找到他们之间共享的参数信息,以实现迁移的方法。这种迁移方式要求的假设条件是: 源域中的数据与目标域中的数据可以共享一些模型的参数。其中的代表性工作主要有[[Zhao et al., 2010](#bookmark324), [Zhao et al., 2011](#bookmark325), [Panet al., 2008b](#bookmark287), [Pan et al., 2008a](#bookmark286)]。图[16](#bookmark96)形象地 表示了基于模型的迁移学习方法的基本思想。 + +![](./media/602723a1d3ce0f3abe7c591a8e4bb6ec.jpg) + +
图 16: 基于模型的迁移学习方法示意图 + +​ 其中,中科院计算所的Zhao等人[[Zhao et al., 2011](#bookmark325)]提出了TransEMDT方法。该方法首先针对已有标记的数据,利用决策树构建鲁棒性的行为识别模型,然后针对无标定数据,利用K-Means聚类方法寻找最优化的标定参数。西安邮电大学的Deng等人[[Deng et al.,2014](#bookmark245)] 也用超限学习机做了类似的工作。香港科技大学的Pan等人[[Pan etal., 2008a](#bookmark286)]利用HMM,针对Wifi室内定位在不同设备、不同时间和不同空间下动态变化的特点,进行不同分布下的室内定位研究。另一部分研究人员对支持向量机 SVM 进行了改进研究 [[Nater et al.,2011](#bookmark285), [Li et al., 2012](#bookmark269)]。这些方法假定 SVM中的权重向量 **w** 可以分成两个部分: **w** = **wo**+**v**, 其中 **w**0代表源域和目标域的共享部分, **v** 代表了对于不同领域的特定处理。在最新的研究成果中,香港科技大学的 Wei 等人 [[Wei et al., 2016b](#bookmark313)]将社交信息加入迁移学习方法的 正则项中,对方法进行了改进。清华大学龙明盛等人[[Long et al., 2015a](#bookmark275), [Long et al., 2016](#bookmark276), [Long etal., 2017](#bookmark280)]改进了深度网络结构,通过在网络中加入概率分布适配层,进一步提高了深度迁移学习网络对于大数据的泛化能力。 + +### 11.2.4 基于关系迁移 + +​ 基于关系的迁移学习方法 (Relation Based Transfer Learning) 与上述三种方法具有截然不同的思路。这种方法比较关注源域和目标域的样本之间的关系。图[17](#bookmark82)形象地表示了不 同领域之间相似的关系。 + +​ 就目前来说,基于关系的迁移学习方法的相关研究工作非常少,仅有几篇连贯式的文章讨论: [[Mihalkova et al., 2007](#bookmark283), [Mihalkova and Mooney,2008](#bookmark284), [Davis and Domingos, 2009](#bookmark244)]。这些文章都借助于马尔科夫逻辑网络(Markov Logic Net)来挖掘不同领域之间的关系相似性。 + +​ 我们将重点讨论基于特征和基于模型的迁移学习方法,这也是目前绝大多数研究工作的热点。 + +![](./media/aa10d36f758430dd4ff72d2bf6a76a6c.jpg) + +
图 17: 基于关系的迁移学习方法示意图 + +![1542812440636](./media/1542812440636.png) + +
图 18: 基于马尔科夫逻辑网的关系迁移 +## 11.3 迁移学习的常用方法 +## 11.3 迁移学习的常见方法有哪些? + +### 11.3.1 数据分布自适应 + +​ 数据分布自适应 (Distribution Adaptation) 是一类最常用的迁移学习方法。这种方法的基本思想是,由于源域和目标域的数据概率分布不同,那么最直接的方式就是通过一些变换,将不同的数据分布的距离拉近。 + +​ 图 [19](#bookmark84)形象地表示了几种数据分布的情况。简单来说,数据的边缘分布不同,就是数据整体不相似。数据的条件分布不同,就是数据整体相似,但是具体到每个类里,都不太相似。 + +![1542812748062](./media/1542812748062.png) + +
图 19: 不同数据分布的目标域数据 + +​ 根据数据分布的性质,这类方法又可以分为边缘分布自适应、条件分布自适应、以及联合分布自适应。下面我们分别介绍每类方法的基本原理和代表性研究工作。介绍每类研究工作时,我们首先给出基本思路,然后介绍该类方法的核心,最后结合最近的相关工作介绍该类方法的扩展。 + +### 11.3.2 边缘分布自适应 + +​ 边缘分布自适应方法 (Marginal Distribution Adaptation) 的目标是减小源域和目标域的边缘概率分布的距离,从而完成迁移学习。从形式上来说,边缘分布自适应方法是用P(X~s~)和 P(X~t~)之间的距离来近似两个领域之间的差异。即: + +​ $DISTANCE(D~s~,D~t~)\approx\lVert P(X_s)-P(X_t)\Vert$ (6.1) + +​ 边缘分布自适应对应于图[19](#bookmark84)中由图[19(a)](#bookmark101)迁移到图[19(b)](#bookmark83)的情形。 + +### 11.3.3 条件分布自适应 + +​ 条件分布自适应方法 (Conditional Distribution Adaptation) 的目标是减小源域和目标域的条件概率分布的距离,从而完成迁移学习。从形式上来说,条件分布自适应方法是用 P(y~s~|X~s~) 和 P (y~t~|X~t~) 之间的距离来近似两个领域之间的差异。即: + +​ $DISTANCE(D~s~,D~t~)\approx\lVert P(y_s|X_s)-P(y_t|X_t)\Vert$(6.8) + +​ 条件分布自适应对应于图[19](#bookmark84)中由图[19(a)](#bookmark101)迁移到图[19(c)](#bookmark85)的情形。 + +​ 目前单独利用条件分布自适应的工作较少,这些工作主要可以在 [[Saito et al.,2017](#bookmark292)] 中找到。最近,中科院计算所的 Wang 等人提出了 STL 方法(Stratified Transfer Learn­ing) [[Wang tal.,2018](#bookmark309)]。作者提出了类内迁移 (Intra-class Transfer)的思想。指出现有的 绝大多数方法都只是学习一个全局的特征变换(Global DomainShift),而忽略了类内的相 似性。类内迁移可以利用类内特征,实现更好的迁移效果。 + +​ STL 方法的基本思路如图所示。首先利用大多数投票的思想,对无标定的位置行为生成伪标;然后在再生核希尔伯特空间中,利用类内相关性进行自适应地空间降维,使得不同情境中的行为数据之间的相关性增大;最后,通过二次标定,实现对未知标定数据的精准标定。 + +![1542817481582](./media/1542817481582.png) + +
图 21: STL 方法的示意图 +### 11.3.4 联合分布自适应 + +​ 联合分布自适应方法 (Joint Distribution Adaptation) 的目标是减小源域和目标域的联合概率分布的距离,从而完成迁移学习。从形式上来说,联合分布自适应方法是用*P*(**x**s) 和P(**x**t)之间的距离、以及P(ys\|**x**s)和P(yt\|**x**t)之间的距离来近似两个领域之间的差异。即: + +​ $DISTANCE(D~s~,D~t~)\approx\lVert P(X_s)-P(X_t)\Vert-\lVert P(y_s|X_s)-P(y_t|X_t)\Vert$(6.10) + +​ 联合分布自适应对应于图[19](#bookmark84)中由图[19(a)](#bookmark101)迁移到图[19(b)](#bookmark83)的情形、以及图[19(a)](#bookmark101)迁移到 +图[19(c)](#bookmark85)的情形。 + +### 11.3.4 概率分布自适应方法优劣性比较 + +综合上述三种概率分布自适应方法,我们可以得出如下的结论: + +1. 精度比较: BDA \>JDA \>TCA \>条件分布自适应。 +2. 将不同的概率分布自适应方法用于神经网络,是一个发展趋势。图[23](#bookmark119)展示的结果表明将概率分布适配加入深度网络中,往往会取得比非深度方法更好的结果。 + +![1542823019007](./media/1542823019007.png) + +
图 22: BDA 方法的效果第二类方法:特征选择 +### 11.3.6 特征选择 + +​ 特征选择法的基本假设是:源域和目标域中均含有一部分公共的特征,在这部分公共的特征,源领域和目标领域的数据分布是一致的。因此,此类方法的目标就是,通过机器学习方法,选择出这部分共享的特征,即可依据这些特征构建模型。 + +​ 图 [24](#bookmark122)形象地表示了特征选择法的主要思路。 + +![1542823210556](./media/1542823210556.png) + +
图 23: 不同分布自适应方法的精度比较 + +![](./media/a3db84158d9b6454adff88dbe4fa5d28.jpg) + +
图 24: 特征选择法示意图 + +​ 这这个领域比较经典的一个方法是发表在 2006 年的 ECML-PKDD 会议上,作者提出了一个叫做 SCL 的方法 (Structural Correspondence Learning) [[Blitzer et al.,2006](#bookmark235)]。这个方法的目标就是我们说的,找到两个领域公共的那些特征。作者将这些公共的特征叫做Pivot feature。找出来这些Pivot feature,就完成了迁移学习的任务。 + +![](./media/4abacd82901988c3e0a98bdb07b2abc6.jpg) + +
图 25: 特征选择法中的 Pivot feature 示意图 + +​ 图 [25](#bookmark124)形象地展示了 Pivot feature 的含义。 Pivot feature指的是在文本分类中,在不同领域中出现频次较高的那些词。总结起来: + +- 特征选择法从源域和目标域中选择提取共享的特征,建立统一模型 +- 通常与分布自适应方法进行结合 +- 通常采用稀疏表示 \|\|**A**\|\|2,1 实现特征选择 + +### 11.3.5 统计特征对齐方法 + +​ 统计特征对齐方法主要将数据的统计特征进行变换对齐。对齐后的数据,可以利用传统机器学习方法构建分类器进行学习。SA方法(Subspace Alignment,子空间对齐)[[Fernando et al.,2013](#bookmark249)]是其中的代表性成果。SA方法直接寻求一个线性变换**M**,将不同的数据实现变换对齐。SA方法的优化目标如下: + +![1542823438846](./media/1542823438846.png) + +则变换 **M** 的值为: + +![1542823455820](./media/1542823455820.png) + +可以直接获得上述优化问题的闭式解: + +![1542823474720](./media/1542823474720.png) + +​ SA 方法实现简单,计算过程高效,是子空间学习的代表性方法。 + +### 11.3.6 流形学习方法 + +**什么是流形学习** + +​ 流形学习自从 2000 年在 Science 上被提出来以后,就成为了机器学习和数据挖掘领域的热门问题。它的基本假设是,现有的数据是从一个高维空间中采样出来的,所以,它具有高维空间中的低维流形结构。流形就是是一种几何对象(就是我们能想像能观测到的)。通俗点说就是,我们无法从原始的数据表达形式明显看出数据所具有的结构特征,那我把它想像成是处在一个高维空间,在这个高维空间里它是有个形状的。一个很好的例子就是星座。满天星星怎么描述?我们想像它们在一个更高维的宇宙空间里是有形状的,这就有了各自星座,比如织女座、猎户座。流形学习的经典方法有Isomap、locally linear embedding、 laplacian eigenmap 等。 + +​ 流形空间中的距离度量:两点之间什么最短?在二维上是直线(线段),可在三维呢?地球上的两个点的最短距离可不是直线,它是把地球展开成二维平面后画的那条直线。那条线在三维的地球上就是一条曲线。这条曲线就表示了两个点之间的最短距离,我们叫它测地线。更通俗一点, 两点之间,测地线最短。在流形学习中,我们遇到测量距离的时候更多的时候用的就是这个测地线。在我们要介绍的 GFK 方法中,也是利用了这个测地线距离。比如在下面的图中,从 A 到 C 最短的距离在就是展开后的线段,但是在三维球体上看它却是一条曲线。 + +![](./media/fcbe02803e45f6455a4602b645b472c5.jpg) + +
图 28: 三维空间中两点之间的距离示意图 + +​ 由于在流形空间中的特征通常都有着很好的几何性质,可以避免特征扭曲,因此我们首先将原始空间下的特征变换到流形空间中。在众多已知的流形中, Grassmann 流形G(d) 可以通过将原始的 d 维子空间 (特征向量)看作它基础的元素,从而可以帮助学习分类 器。在 Grassmann流形中,特征变换和分布适配通常都有着有效的数值形式,因此在迁移学习问题中可以被很高效地表示和求解 [[Hamm and Lee,2008](#bookmark260)]。因此,利用 Grassmann流形空间中来进行迁移学习是可行的。现存有很多方法可以将原始特征变换到流形空间 中[[Gopalan et al., 2011](#bookmark257), [Baktashmotlagh et al.,2014](#bookmark230)]。 + +​ 在众多的基于流形变换的迁移学习方法中,GFK(Geodesic Flow Kernel)方法[[Gong et +al., 2012](#bookmark255)]是最为代表性的一个。GFK是在2011年发表在ICCV上的SGF方法[[Gopalan et al., +2011](#bookmark257)]发展起来的。我们首先介绍SGF方法。 + +​ SGF 方法从增量学习中得到启发:人类从一个点想到达另一个点,需要从这个点一步一步走到那一个点。那么,如果我们把源域和目标域都分别看成是高维空间中的两个点,由源域变换到目标域的过程不就完成了迁移学习吗?也就是说, 路是一步一步走出来的。 + +​ 于是 SGF 就做了这个事情。它是怎么做的呢?把源域和目标域分别看成高维空间 (即Grassmann流形)中的两个点,在这两个点的测地线距离上取d个中间点,然后依次连接起来。这样,源域和目标域就构成了一条测地线的路径。我们只需要找到合适的每一步的变换,就能从源域变换到目标域了。图 [29](#bookmark133)是 SGF 方法的示意图。 + +![](./media/103de3658cbb97ad4c24bafe28f9d957.jpg) + +
图 29: SGF 流形迁移学习方法示意图 + +​ SGF 方法的主要贡献在于:提出了这种变换的计算及实现了相应的算法。但是它有很明显的缺点:到底需要找几个中间点? SGF也没能给出答案,就是说这个参数d是没法估计的,没有一个好的方法。这个问题在 GFK 中被回答了。 + +​ GFK方法首先解决SGF的问题:如何确定中间点的个数d。它通过提出一种核学习的方法,利用路径上的无穷个点的积分,把这个问题解决了。这是第一个贡献。然后,它又解决了第二个问题:当有多个源域的时候,我们如何决定使用哪个源域跟目标域进行迁移? GFK通过提出Rank of Domain度量,度量出跟目标域最近的源域,来解决这个问题。图 [30](#bookmark134)是 GFK 方法的示意图。 + +![](./media/e654d14df0b44ee4e8a0e505c654044b.jpg) + +
图 30: GFK 流形迁移学习方法示意图 + +​ 用Ss和St分别表示源域和目标域经过主成分分析(PCA)之后的子空间,则G可以视为所有的d维子空间的集合。每一个d维的原始子空间都可以被看作G上的一个点。因此,在两点之间的测地线{\$(t) :0 \< t \<1}可以在两个子空间之间构成一条路径。如果我 们令Ss = \$(0),St =\$(1),则寻找一条从\$(0)到\$(1)的测地线就等同于将原始的特征变换到一个无穷维度的空间中,最终减小域之间的漂移现象。这种方法可以被看作是一种从\$(0)到\$(1)的増量式“行走”方法。 + +​ 特别地,流形空间中的特征可以被表示为**z** =\$(t)T**x**。变换后的特征**Z**i和**Z**j的内积定义了一个半正定 (positive semidefinite) 的测地线流式核 + +![1542823895008](./media/1542823895008.png) + +​ GFK 方法详细的计算过程可以参考原始的文章,我们在这里不再赘述。 + +### 11.3.7 什么是finetune? + +​ 深度网络的finetune也许是最简单的深度网络迁移方法。**Finetune**,也叫微调、fine-tuning, 是深度学习中的一个重要概念。简而言之,finetune就是利用别人己经训练好的网络,针对自己的任务再进行调整。从这个意思上看,我们不难理解finetune是迁移学习的一部分。 + +**为什么需要已经训练好的网络?** + +​ 在实际的应用中,我们通常不会针对一个新任务,就去从头开始训练一个神经网络。这样的操作显然是非常耗时的。尤其是,我们的训练数据不可能像ImageNet那么大,可以训练出泛化能力足够强的深度神经网络。即使有如此之多的训练数据,我们从头开始训练,其代价也是不可承受的。 + +​ 那么怎么办呢?迁移学习告诉我们,利用之前己经训练好的模型,将它很好地迁移到自己的任务上即可。 + +**为什么需要 finetune?** + +​ 因为别人训练好的模型,可能并不是完全适用于我们自己的任务。可能别人的训练数据和我们的数据之间不服从同一个分布;可能别人的网络能做比我们的任务更多的事情;可能别人的网络比较复杂,我们的任务比较简单。 + +​ 举一个例子来说,假如我们想训练一个猫狗图像二分类的神经网络,那么很有参考价值的就是在 CIFAR-100 上训练好的神经网络。但是 CIFAR-100 有 100 个类别,我们只需要 2个类别。此时,就需要针对我们自己的任务,固定原始网络的相关层,修改网络的输出层以使结果更符合我们的需要。 + +​ 图[36](#bookmark148)展示了一个简单的finetune过程。从图中我们可以看到,我们采用的预训练好的网络非常复杂,如果直接拿来从头开始训练,则时间成本会非常高昂。我们可以将此网络进行改造,固定前面若干层的参数,只针对我们的任务,微调后面若干层。这样,网络训练速度会极大地加快,而且对提高我们任务的表现也具有很大的促进作用。 + +![](./media/b1630ca5d004d4b430672c8b8ce7fb90.jpg) + +
图 36: 一个简单的 finetune 示意图 +**Finetune 的优势** + +​ Finetune 的优势是显然的,包括: + +- 不需要针对新任务从头开始训练网络,节省了时间成本; +- 预训练好的模型通常都是在大数据集上进行的,无形中扩充了我们的训练数据,使得模型更鲁棒、泛化能力更好; +- Finetune 实现简单,使得我们只关注自己的任务即可。 + +**Finetune 的扩展** + +​ 在实际应用中,通常几乎没有人会针对自己的新任务从头开始训练一个神经网络。Fine-tune 是一个理想的选择。 + +​ Finetune 并不只是针对深度神经网络有促进作用,对传统的非深度学习也有很好的效果。例如, finetune对传统的人工提取特征方法就进行了很好的替代。我们可以使用深度网络对原始数据进行训练,依赖网络提取出更丰富更有表现力的特征。然后,将这些特征作为传统机器学习方法的输入。这样的好处是显然的: 既避免了繁复的手工特征提取,又能自动地提取出更有表现力的特征。 + +​ 比如,图像领域的研究,一直是以 SIFT、SURF 等传统特征为依据的,直到 2014 年,伯克利的研究人员提出了 DeCAF特征提取方法[[Donahue et al.,2014](#bookmark246)],直接使用深度卷积神经网络进行特征提取。实验结果表明,该特征提取方法对比传统的图像特征,在精度上有着无可匹敌的优势。另外,也有研究人员用卷积神经网络提取的特征作为SVM分类器的输 入[[Razavian et al.,014](#bookmark291)],显著提升了图像分类的精度。 + +### 11.3.8 finetune为什么有效? + +​ 随着 AlexNet [[Krizhevsky et al., 2012](#bookmark268)] 在 2012 年的 ImageNet大赛上获得冠军,深度学习开始在机器学习的研究和应用领域大放异彩。尽管取得了很好的结果,但是神经网络本身就像一个黑箱子,看得见,摸不着,解释性不好。由于神经网络具有良好的层次结构很自然地就有人开始关注,能否通过这些层次结构来很好地解释网络?于是,有了我们熟知的例子:假设一个网络要识别一只猫,那么一开始它只能检测到一些边边角角的东西,和猫根本没有关系;然后可能会检测到一些线条和圆形;慢慢地,可以检测到有猫的区域;接着是猫腿、猫脸等等。图 [32](#bookmark137)是一个简单的示例。 + +![1542824195602](./media/1542824195602.png) + +
图 32: 深度神经网络进行特征提取到分类的简单示例 + +​ 这表达了一个什么事实呢?概括来说就是:前面几层都学习到的是通用的特征(general feature);随着网络层次的加深,后面的网络更偏重于学习任务特定的特征(specific feature)。 +这非常好理解,我们也都很好接受。那么问题来了:如何得知哪些层能够学习到 general feature,哪些层能够学习到specific feature。更进一步:如果应用于迁移学习,如何决定该迁移哪些层、固定哪些层? + +​ 这个问题对于理解神经网络以及深度迁移学习都有着非常重要的意义。 + +​ 来自康奈尔大学的 Jason Yosinski 等人 [[Yosinski et al., 2014](#bookmark318)]率先进行了深度神经网络可迁移性的研究,将成果发表在2014年机器学习领域顶级会议NIPS上并做了口头汇报。该论文是一篇实验性质的文章(通篇没有一个公式)。其目的就是要探究上面我们提到的几个关键性问题。因此,文章的全部贡献都来自于实验及其结果。(别说为啥做实验也能发文章:都是高考,我只上了个普通一本,我高中同学就上了清华) + +​ 在ImageNet的1000类上,作者把1000类分成两份(A和B),每份500个类别。然后,分别对A和B基于Caffe训练了一个AlexNet网络。一个AlexNet网络一共有8层, 除去第8层是类别相关的网络无法迁移以外,作者在 1 到 7这 7层上逐层进行 finetune 实验,探索网络的可迁移性。 + +​ 为了更好地说明 finetune 的结果,作者提出了有趣的概念: AnB 和 BnB。 + +​ 迁移A网络的前n层到B (AnB) vs固定B网络的前n层(BnB) + +​ 简单说一下什么叫AnB:(所有实验都是针对数据B来说的)将A网络的前n层拿来并将它frozen,剩下的8 - n层随机初始化,然后对B进行分类。 + +​ 相应地,有BnB:把训练好的B网络的前n层拿来并将它frozen,剩下的8 - n层随机初始化,然后对 B 进行分类。 + +​ **实验结果** + +​ 实验结果如下图(图[33](#bookmark145)) 所示: + +​ 这个图说明了什么呢?我们先看蓝色的BnB和BnB+(就是BnB加上finetune)。对 BnB而言,原训练好的 B 模型的前 3 层直接拿来就可以用而不会对模型精度有什么损失到了第4 和第5 层,精度略有下降,不过还是可以接受。然而到了第6 第第7层,精度居然奇迹般地回升了!这是为什么?原因如下:对于一开始精度下降的第4 第 5 层来说,确 + +![1542824318155](./media/1542824318155.png) + +
图 33: 深度网络迁移实验结果 1 + +实是到了这一步,feature变得越来越specific,所以下降了。那对于第6第7层为什么精度又不变了?那是因为,整个网络就8层,我们固定了第6第7层,这个网络还能学什么呢?所以很自然地,精度和原来的 B 网络几乎一致! + +​ 对 BnB+ 来说,结果基本上都保持不变。说明 finetune 对模型结果有着很好的促进作用! + +​ 我们重点关注AnB和AnB+。对AnB来说,直接将A网络的前3层迁移到B,貌似不会有什么影响,再一次说明,网络的前3层学到的几乎都是general feature!往后,到了第4第5层的时候,精度开始下降,我们直接说:一定是feature不general 了!然而,到了第6第7层,精度出现了小小的提升后又下降,这又是为什么?作者在这里提出两点co-adaptation和feature representation。就是说,第4第5层精度下降的时候,主要是由于A和B两个数据集的差异比较大,所以会下降;至I」了第6第7层,由于网络几乎不迭代了,学习能力太差,此时 feature 学不到,所以精度下降得更厉害。 + +​ 再看AnB+。加入了 finetune以后,AnB+的表现对于所有的n几乎都非常好,甚至 比baseB +(最初的B)还要好一些!这说明:finetune对于深度迁移有着非常好的促进作用! + +​ 把上面的结果合并就得到了下面一张图 (图[34](#bookmark138)): + +​ 至此, AnB 和 BnB 基本完成。作者又想,是不是我分 A 和 B 数据的时候,里面存在一些比较相似的类使结果好了?比如说A里有猫,B里有狮子,所以结果会好?为了排除这些影响,作者又分了一下数据集,这次使得A和B里几乎没有相似的类别。在这个条件下再做AnB,与原来精度比较(0%为基准)得到了下图(图[35](#bookmark139)): + +​ 这个图说明了什么呢?简单:随着可迁移层数的增加,模型性能下降。但是,前3层仍然还是可以迁移的!同时,与随机初始化所有权重比较,迁移学习的精度是很高的!总之: + +- 深度迁移网络要比随机初始化权重效果好; + + +- 网络层数的迁移可以加速网络的学习和优化。 + +### 11.3.9 什么是深度网络自适应? + +**基本思路** + +​ 深度网络的 finetune 可以帮助我们节省训练时间,提高学习精度。但是 finetune 有它的先天不足:它无法处理训练数据和测试数据分布不同的情况。而这一现象在实际应用中比比皆是。因为 finetune 的基本假设也是训练数据和测试数据服从相同的数据分布。这在迁移学习中也是不成立的。因此,我们需要更进一步,针对深度网络开发出更好的方法使之更好地完成迁移学习任务。 + +​ 以我们之前介绍过的数据分布自适应方法为参考,许多深度学习方法[[Tzeng et al.,2014](#bookmark307), [Long et al.,2015a](#bookmark275)]都开发出了自适应层(AdaptationLayer)来完成源域和目标域数据的自适应。自适应能够使得源域和目标域的数据分布更加接近,从而使得网络的效果更好。 + +​ 从上述的分析我们可以得出,深度网络的自适应主要完成两部分的工作: + +​ 一是哪些层可以自适应,这决定了网络的学习程度; + +​ 二是采用什么样的自适应方法 (度量准则),这决定了网络的泛化能力。 + +​ 深度网络中最重要的是网络损失的定义。绝大多数深度迁移学习方法都采用了以下的损失定义方式: + +![1542824918145](./media/1542824918145.png) + +​ 其中,I表示网络的最终损失,lc(Ds,**y**s)表示网络在有标注的数据(大部分是源域)上的常规分类损失(这与普通的深度网络完全一致),Ia(Ds,Dt)表示网络的自适应损失。最后一部分是传统的深度网络所不具有的、迁移学习所独有的。此部分的表达与我们先前讨论过的源域和目标域的分布差异,在道理上是相同的。式中的A是权衡两部分的权重参数。 + +​ 上述的分析指导我们设计深度迁移网络的基本准则:决定自适应层,然后在这些层加入自适应度量,最后对网络进行 finetune。 + +### 11.3.10 GAN在迁移学习中的应用 + +生成对抗网络 GAN(Generative Adversarial Nets) [[Goodfellow et al.,2014](#bookmark256)] 是目前人工智能领域最炙手可热的概念之一。其也被深度学习领军人物 Yann Lecun 评为近年来最令人欣喜的成就。由此发展而来的对抗网络,也成为了提升网络性能的利器。本小节介绍深度对抗网络用于解决迁移学习问题方面的基本思路以及代表性研究成果。 + +**基本思路** + +​ GAN 受到自博弈论中的二人零和博弈 (two-player game) 思想的启发而提出。它一共包括两个部分:一部分为生成网络(Generative Network),此部分负责生成尽可能地以假乱真的样本,这部分被成为生成器(Generator);另一部分为判别网络(Discriminative Network), 此部分负责判断样本是真实的,还是由生成器生成的,这部分被成为判别器(Discriminator) 生成器和判别器的互相博弈,就完成了对抗训练。 + +​ GAN 的目标很明确:生成训练样本。这似乎与迁移学习的大目标有些许出入。然而,由于在迁移学习中,天然地存在一个源领域,一个目标领域,因此,我们可以免去生成样本的过程,而直接将其中一个领域的数据 (通常是目标域) 当作是生成的样本。此时,生成器的职能发生变化,不再生成新样本,而是扮演了特征提取的功能:不断学习领域数据的特征使得判别器无法对两个领域进行分辨。这样,原来的生成器也可以称为特征提取器 +(Feature Extractor)。 + +​ 通常用 Gf 来表示特征提取器,用 Gd 来表示判别器。正是基于这样的领域对抗的思想,深度对抗网络可以被很好地运用于迁移学习问题中。与深度网络自适应迁移方法类似,深度对抗网络的损失也由两部分构成:网络训练的损失lc*和领域判别损失Id: + +![1542826334834](./media/1542826334834.png) + +**DANN** + +Yaroslav Ganin 等人 [[Ganin et al., 2016](#bookmark251)]首先在神经网络的训练中加入了对抗机制,作者将他们的网络称之为DANN(Domain-Adversarial Neural Network)。在此研宄中,网络的学习目标是:生成的特征尽可能帮助区分两个领域的特征,同时使得判别器无法对两个领域的差异进行判别。该方法的领域对抗损失函数表示为: + +![1542826461988](./media/1542826461988.png) + +Id = max 其中的 Ld 表示为 + +![1542826475517](./media/1542826475517.png) + + + + + +## 参考文献 + +王晋东,迁移学习简明手册 + +[Baktashmotlagh et al., 2013] Baktashmotlagh, M., Harandi, M. T., Lovell, B. C.,and Salz- mann, M. (2013). Unsupervised domain adaptation by domain invariant projection. In *ICCV,* pages 769-776. + +[Baktashmotlagh et al., 2014] Baktashmotlagh, M., Harandi, M. T., Lovell, B. C., and Salz- mann, M. (2014). Domain adaptation on the statistical manifold. In Proceedings of the IEEE Conference on Computer Vision and Pattern Recognition*,pages 2481-2488. + +[Ben-David et al., 2010] Ben-David, S., Blitzer, J., Crammer, K., Kulesza, A., Pereira, F., and Vaughan, J. W. (2010). A theory of learning from different domains. *Machine learning,* 79(1-2):151-175. + +[Ben-David et al., 2007] Ben-David, S., Blitzer, J., Crammer, K., and Pereira, F. (2007). Analysis of representations for domain adaptation. In *NIPS*, pages 137-144. + +[Blitzer et al., 2008] Blitzer, J., Crammer, K., Kulesza, A., Pereira, F., and Wortman, J. (2008). Learning bounds for domain adaptation. In *Advances in neural information processing systems*, pages 129-136. + +[Blitzer et al., 2006] Blitzer, J., McDonald, R., and Pereira, F. (2006). Domain adaptation with structural correspondence learning. In *Proceedings of the 2006 conference on empiri­cal methods in natural language processing*, pages 120-128. Association for Computational Linguistics. + +[Borgwardt et al., 2006] Borgwardt, K. M., Gretton, A., Rasch, M. J., Kriegel, H.-P., Scholkopf, B., and Smola, A. J. (2006). Integrating structured biological data by kernel maximum mean discrepancy. *Bioinformatics*, 22(14):e49-e57. + +[Bousmalis et al., 2016] Bousmalis, K., Trigeorgis, G., Silberman, N., Krishnan, D., and Erhan, D. (2016). Domain separation networks. In *Advances in Neural Information Processing Systems*, pages 343-351. + +[Cai et al., 2011] Cai, D., He, X., Han, J., and Huang, T. S. (2011). Graph regularized nonnegative matrix factorization for data representation. *IEEE Transactions on Pattern Analysis and Machine Intelligence*, 33(8):1548-1560. + +[Cao et al., 2017] Cao, Z., Long, M., Wang, J., and Jordan, M. I. (2017). Partial transfer learning with selective adversarial networks. *arXiv preprint arXiv:1707.07901*. + +[Carlucci et al., 2017] Carlucci, F. M., Porzi, L., Caputo, B., Ricci, E., and Bulo, S. R. (2017). Autodial: Automatic domain alignment layers. In International Conference on* Computer Vision. + +[Cook et al., 2013] Cook, D., Feuz, K. D., and Krishnan, N. C. (2013). Transfer learning for activity recognition: A survey. *Knowledge and information systems*, 36(3):537-556. + +[Cortes et al., 2008] Cortes, C., Mohri, M., Riley, M., and Rostamizadeh, A. (2008). Sample selection bias correction theory. In *International Conference on Algorithmic Learning Theory*, pages 38-53, Budapest, Hungary. Springer. + +[Dai et al., 2007] Dai, W., Yang, Q., Xue, G.-R., and Yu, Y. (2007). Boosting for transfer learning. In *ICML*, pages 193-200. ACM. + +[Davis and Domingos, 2009] Davis, J. and Domingos, P. (2009). Deep transfer via second- order markov logic. In *Proceedings of the 26th annual international conference on machine learning*, pages 217-224. ACM. + +[Denget al., 2014] Deng,W.,Zheng,Q.,andWang,Z.(2014).Cross-personactivityrecog-nition using reduced kernel extreme learning machine. *Neural Networks,* 53:1-7. + +[Donahue et al., 2014] Donahue, J., Jia, Y., et al. (2014). Decaf: A deep convolutional activation feature for generic visual recognition. In *ICML*, pages 647-655. + +[Dorri and Ghodsi, 2012] Dorri, F. and Ghodsi, A. (2012). Adapting component analysis. In *Data Mining (ICDM), 2012 IEEE 12th International Conference on*, pages 846-851. IEEE. + +[Duan et al., 2012] Duan, L., Tsang, I. W., and Xu, D. (2012). Domain transfer multi­ple kernel learning. *IEEE Transactions on Pattern Analysis and Machine Intelligence*, 34(3):465-479. + +[Fernando et al., 2013] Fernando, B., Habrard, A., Sebban, M., and Tuytelaars, T. (2013). Unsupervised visual domain adaptation using subspace alignment. In ICCV*, pages 2960­2967. + +[Fodor, 2002] Fodor, I. K. (2002). A survey of dimension reduction techniques. Center for Applied Scientific Computing, Lawrence Livermore National Laboratory*, 9:1-18. + +[Ganin et al., 2016] Ganin, Y., Ustinova, E., Ajakan, H., Germain, P., Larochelle, H., Lavi- olette, F., Marchand, M., and Lempitsky, V. (2016).Domain-adversarial training of neural networks. *Journal of Machine Learning +Research*, 17(59):1-35. + +[Gao et al., 2012] Gao, C., Sang, N., and Huang, R. (2012). Online transfer boosting for object tracking. In *Pattern Recognition (ICPR), 2012 21st International Conference on*, pages 906-909. IEEE. + +[Ghifary et al., 2017] Ghifary, M., Balduzzi, D., Kleijn, W. B., and Zhang, M. (2017). Scat­ter component analysis: A unified framework for domain adaptation and domain general­ization. *IEEE transactions on pattern analysis and machine intelligence*, 39(7):1414-1430. + +[Ghifary et al., 2014] Ghifary, M., Kleijn, W. B., and Zhang, M. (2014). Domain adaptive neural networks for object recognition. In *PRICAI*, pages 898-904. + +[Gong et al., 2012] Gong, B., Shi, Y., Sha, F., and Grauman, K. (2012). Geodesic flow kernel for unsupervised domain adaptation. In *CVPR*, pages 2066-2073. + +[Goodfellow et al., 2014] Goodfellow, I., Pouget-Abadie, J., Mirza, M., Xu, B., Warde- Farley, D., Ozair, S., Courville, A., and Bengio, Y. (2014). Generative adversarial nets. In *Advances in neural information processing systems*, pages 2672-2680. + +[Gopalan et al., 2011] Gopalan, R., Li, R., and Chellappa, R. (2011). Domain adaptation for object recognition: An unsupervised approach. In *ICCV*, pages 999-1006. IEEE. + +[Gretton et al., 2012] Gretton, A., Sejdinovic, D., Strathmann, H., Balakrishnan, S., Pontil, M., Fukumizu, K., and Sriperumbudur, B. K. (2012). Optimal kernel choice for large- scale two-sample tests. In *Advances in neural information processing systems*, pages 1205-1213. + +[Gu et al., 2011] Gu, Q., Li, Z., Han, J., et al. (2011). Joint feature selection and subspace learning. In *IJCAI Proceedings-International Joint Conference on Artificial Intel ligence*, volume 22, page 1294. + +[Hamm and Lee, 2008] Hamm, J. and Lee, D. D. (2008). Grassmann discriminant analysis: a unifying view on subspace-based learning. In *ICML*, pages 376-383. ACM. + +[Hou et al., 2015] Hou, C.-A., Yeh, Y.-R., and Wang, Y.-C. F. (2015). An unsupervised domain adaptation approach for cross-domain visual classification. In *Advanced Video and Signal Based Surveil lance (AVSS), 2015 12th IEEE International Conference on*,pages 1-6. IEEE. + +[Hsiao et al., 2016] Hsiao, P.-H., Chang, F.-J., and Lin, Y.-Y. (2016). Learning discrim­inatively reconstructed source data for object recognition with few examples. *IEEE*Transactions on Image Processing*, 25(8):3518-3532. + +[Hu and Yang, 2011] Hu, D. H. and Yang, Q. (2011). Transfer learning for activity recog­nition via sensor mapping. In *IJCAI Proceedings-International Joint Conference on Artificial Intelligence*, volume 22, page 1962, Barcelona, Catalonia, Spain. IJCAI. + +[Huang et al., 2007] Huang, J., Smola, A. J., Gretton, A., Borgwardt, K. M., Scholkopf, B., et al. (2007). Correcting sample selection bias by unlabeled data. *Advances in neural information processing systems*, 19:601. + +[Jaini et al., 2016] Jaini, P., Chen, Z., Carbajal, P., Law, E., Middleton, L., Regan, K., Schaekermann, M., Trimponias, G., Tung, J., and Poupart, P. (2016). Online bayesian transfer learning for sequential data modeling. In *ICLR 2017*. + +[Kermany et al., 2018] Kermany, D. S., Goldbaum, M., Cai, W., Valentim, C. C., Liang, H., Baxter, S. L., McKeown, A., Yang, G., Wu, X., Yan, F., et al. (2018). Identifying medical diagnoses and treatable diseases by image-based deep learning. *Cell*, 172(5):1122-1131. + +[Khan and Heisterkamp, 2016] Khan, M. N. A. and Heisterkamp, D. R. (2016). Adapting instance weights for unsupervised domain adaptation using quadratic mutual informa­tion and subspace learning. In *Pattern Recognition (ICPR), 2016 23rd International Conference on*, pages 1560-1565, Mexican City. IEEE. + +[Krizhevsky et al., 2012] Krizhevsky, A., Sutskever, I., and Hinton, G. E. (2012). Imagenet classification with deep convolutional neural networks. In Advances in neural information processing systems*, pages 1097-1105. + +[Li et al., 2012] Li, H., Shi, Y., Liu, Y., Hauptmann, A. G., and Xiong, Z. (2012). Cross­domain video concept detection: A joint discriminative and generative active learning approach. *Expert Systems with Applications*, +39(15):12220-12228. + +[Li et al., 2016] Li, J., Zhao, J., and Lu, K. (2016). Joint feature selection and structure preservation for domain adaptation. In *Proceedings of the Twenty-Fifth International Joint Conference on Artificial Intelligence*, pages +1697-1703. AAAI Press. + +[Li et al., 2018] Li, Y., Wang, N., Shi, J., Hou, X., and Liu, J. (2018). Adaptive batch normalization for practical domain adaptation. *Pattern Recognition*, 80:109-117. + +[Liu et al., 2011] Liu, J., Shah, M., Kuipers, B., and Savarese, S. (2011). Cross-view action recognition via view knowledge transfer. In *Computer Vision and Pattern Recognition (CVPR), 2011 IEEE Conference on*, pages 3209-3216, Colorado Springs, CO, USA. IEEE. + +[Liu and Tuzel, 2016] Liu, M.-Y. and Tuzel, O. (2016). Coupled generative adversarial networks. In *Advances in neural information processing systems*, pages 469-477. + +[Liu et al., 2017] Liu, T., Yang, Q., and Tao, D. (2017). Understanding how feature struc­ture transfers in transfer learning. In *IJCAI*. + +[Long et al., 2015a] Long, M., Cao, Y., Wang, J., and Jordan, M. (2015a). Learning trans­ferable features with deep adaptation networks. In *ICML*, pages 97-105. + +[Long et al., 2016] Long, M., Wang, J., Cao, Y., Sun, J., and Philip, S. Y. (2016). Deep learning of transferable representation for scalable domain adaptation. *IEEE Transac­tions on Knowledge and Data Engineering*, +28(8):2027-2040. + +[Long et al., 2014a] Long, M., Wang, J., Ding, G., Pan, S. J., and Yu, P. S. (2014a). Adaptation regularization: A general framework for transfer learning.*IEEE TKDE, 26(5):1076-1089. + +[Long et al., 2014b] Long, M., Wang, J., Ding, G., Sun, J., and Yu, P. S. (2014b). Transfer joint matching for unsupervised domain adaptation. In *CVPR ,pages 1410-1417. + +[Long et al., 2013] Long, M., Wang, J., et al. (2013). Transfer feature learning with joint distribution adaptation. In *ICCV*, pages 2200-2207. + +[Long et al., 2017] Long, M., Wang, J., and Jordan, M. I. (2017). Deep transfer learning with joint adaptation networks. In *ICML*, pages 2208-2217. + +[Long et al., 2015b] Long, M., Wang, J., Sun, J., and Philip, S. Y. (2015b). Domain invari­ant transfer kernel learning. *IEEE Transactions on Knowledge and Data Engineering*, 27(6):1519-1532. + +[Luo et al., 2017] Luo, Z., Zou, Y., Hoffman, J., and Fei-Fei, L. F. (2017). Label efficient learning of transferable representations acrosss domains and tasks. In *Advances in Neural Information Processing Systems*, pages 164-176. + +[Mihalkova et al., 2007] Mihalkova, L., Huynh, T., and Mooney, R. J. (2007). Mapping and revising markov logic networks for transfer learning. In *AAAI*, volume 7, pages 608-614. + +[Mihalkova and Mooney, 2008] Mihalkova, L. and Mooney, R. J. (2008). Transfer learning by mapping with minimal target data. In *Proceedings of the AAAI-08 workshop on transfer learning for complex tasks*. + +[Nater et al., 2011] Nater, F., Tommasi, T., Grabner, H., Van Gool, L., and Caputo, B. (2011). Transferring activities: Updating human behavior analysis. In *Computer Vision Workshops (ICCV Workshops), 2011 IEEE International Conference on*, pages 1737­1744, Barcelona, Spain. IEEE. + +[Pan et al., 2008a] Pan, S. J., Kwok, J. T., and Yang, Q. (2008a). Transfer learning via dimensionality reduction. In *Proceedings of the 23rd AAAI conference on Artificial in­telligence*, volume 8, pages 677-682. + +[Pan et al., 2008b] Pan, S. J., Shen, D., Yang, Q., and Kwok, J. T. (2008b). Transferring localization models across space. In *Proceedings of the 23rd AAAI Conference on Artificial Intelligence*, pages 1383-1388. + +[Pan et al., 2011] Pan, S. J., Tsang, I. W., Kwok, J. T., and Yang, Q. (2011). Domain adaptation via transfer component analysis. *IEEE TNN*, 22(2):199-210. + +[PanandYang, 2010] Pan,S.J.andYang,Q.(2010). A survey on transfer learning. IEEE TKDE*, 22(10):1345-1359. + +[Patil and Phursule, 2013] Patil, D. M. and Phursule, R. (2013). Knowledge transfer using cost sensitive online learning classification. *International Journal of Science and Research*, pages 527-529. + +[Razavian et al., 2014] Razavian, A. S., Azizpour, H., Sullivan, J., and Carlsson, S. (2014). Cnn features off-the-shelf: an astounding baseline for recognition. In *Computer Vision and Pattern Recognition Workshops (CVPRW), 2014 IEEE Conference on*, pages 512­519. IEEE. + +[Saito et al., 2017] Saito, K., Ushiku, Y., and Harada, T. (2017). Asymmetric tri-training for unsupervised domain adaptation. In *International Conference on Machine Learning*. + +[Sener et al., 2016] Sener, O., Song, H. O., Saxena, A., and Savarese, S. (2016). Learning transferrable representations for unsupervised domain adaptation. In *Advances in Neural Information Processing Systems*, pages 2110-2118. + +[Shen et al., 2018] Shen, J., Qu, Y., Zhang, W., and Yu, Y. (2018). Wasserstein distance guided representation learning for domain adaptation. In *AAAI*. + +[Si et al., 2010] Si, S., Tao, D., and Geng, B. (2010). Bregman divergence-based regu­larization for transfer subspace learning. *IEEE Transactions on Knowledge and Data Engineering*, 22(7):929-942. + +[Silver et al., 2017] Silver, D., Schrittwieser, J., Simonyan, K., Antonoglou, I., Huang, A., Guez, A., Hubert, T., Baker, L., Lai, M., Bolton, A., et al. (2017). Mastering the game of go without human knowledge. *Nature*, 550(7676):354. + +[Stewart and Ermon, 2017] Stewart, R. and Ermon, S. (2017). Label-free supervision of neural networks with physics and domain knowledge. In *AAAI*, pages 2576-2582. + +[Sun et al., 2016] Sun, B., Feng, J., and Saenko, K. (2016). Return of frustratingly easy domain adaptation. In *AAAI*, volume 6, page 8. + +[Sun and Saenko, 2015] Sun, B. and Saenko, K. (2015). Subspace distribution alignment for unsupervised domain adaptation. In *BMVC*, pages 24-1. + +[Sun and Saenko, 2016] Sun, B. and Saenko, K. (2016). Deep coral: Correlation alignment for deep domain adaptation. In *European Conference on Computer Vision*, pages 443-450. Springer. + +[Tahmoresnezhad and Hashemi, 2016] Tahmoresnezhad, J. and Hashemi, S. (2016). Visual domain adaptation via transfer feature learning. *Knowledge and Information Systems*, pages 1-21. + +[Tan et al., 2015] Tan, B., Song, Y., Zhong, E., and Yang, Q. (2015). Transitive trans­fer learning. In *Proceedings of the 21th ACM SIGKDD International Conference on Knowledge Discovery and Data Mining*, pages 1155-1164. ACM. + +[Tan et al., 2017] Tan, B., Zhang, Y., Pan, S. J., and Yang, Q. (2017). Distant domain transfer learning. In *Thirty-First AAAI Conference on Artificial Intelligence*. + +[Taylor and Stone, 2009] Taylor, M. E. and Stone, P. (2009). Transfer learning for reinforce­ment learning domains: A survey. *Journal of Machine Learning Research*, 10(Jul):1633- 1685. + +[Tzeng et al., 2015] Tzeng, E., Hoffman, J., Darrell, T., and Saenko, K. (2015). Simulta­neous deep transfer across domains and tasks. In *Proceedings of the IEEE International Conference on Computer Vision*, pages 4068-4076, Santiago, Chile. IEEE. + +[Tzeng et al., 2017] Tzeng, E., Hoffman, J., Saenko, K., and Darrell, T. (2017). Adversarial discriminative domain adaptation. In *CVPR*, pages 2962-2971. + +[Tzeng et al., 2014] Tzeng, E., Hoffman, J., Zhang, N., et al. (2014). Deep domain confu­sion: Maximizing for domain invariance. *arXiv preprint arXiv:1412.3474*. + +[Wang et al., 2017] Wang, J., Chen, Y., Hao, S., et al. (2017). Balanced distribution adap­tation for transfer learning. In *ICDM*, pages 1129-1134. + +[Wang et al., 2018] Wang, J., Chen, Y., Hu, L., Peng, X., and Yu, P. S. (2018). Strati­fied transfer learning for cross-domain activity recognition. In *2018 IEEE International Conference on Pervasive Computing and Communications (PerCom)*. + +[Wang et al., 2014] Wang, J., Zhao, P., Hoi, S. C., and Jin, R. (2014). Online feature selection and its applications. *IEEE Transactions on Knowledge and Data Engineering*, 26(3):698-710. + +[Wei et al., 2016a] Wei, P., Ke, Y., and Goh, C. K. (2016a). Deep nonlinearfeature coding for unsupervised domain adaptation. In *IJCAI*, pages 2189-2195. + +[Wei et al., 2017] Wei, Y., Zhang, Y., and Yang, Q. (2017). Learning totransfer. *arXiv* preprint arXiv:1708.05629*. + +[Wei et al., 2016b] Wei, Y., Zhu, Y., Leung, C. W.-k., Song, Y., and Yang, Q. (2016b). Instilling social to physical: Co-regularized heterogeneous transfer learning. In *Thirtieth* AAAI Conference on Artificial Intelligence*. + +[Weiss et al., 2016] Weiss, K., Khoshgoftaar, T. M., and Wang, D. (2016). A survey of transfer learning. *Journal of Big Data*, 3(1):1-40. + +[Wu et al., 2017] Wu, Q., Zhou, X., Yan, Y., Wu, H., and Min, H. (2017). Online transfer learning by leveraging multiple source domains. *Knowledge and Information Systems*, 52(3):687-707. + +[xinhua, 2016] xinhua (2016). http://mp.weixin.qq.com/s?__biz=MjM5ODYzNzAyMQ==& mid=2651933920&idx=1\\&sn=ae2866bd12000f1644eae1094497837e. + +[Yan et al., 2017] Yan, Y., Wu, Q., Tan, M., Ng, M. K., Min, H., and Tsang, I. W. (2017). Online heterogeneous transfer by hedge ensemble of offline and online decisions. *IEEE transactions on neural networks and learning systems*. + +[Yosinski et al., 2014] Yosinski, J., Clune, J., Bengio, Y., and Lipson, H. (2014). How transferable are features in deep neural networks? In *Advances in neural information processing systems*, pages 3320-3328. + +[Zadrozny, 2004] Zadrozny, B. (2004). Learning and evaluating classifiers under sample selection bias. In *Proceedings of the twenty-first international conference on Machine learning*, page 114, Alberta, Canada. ACM. + +[Zellinger et al., 2017] Zellinger, W., Grubinger, T., Lughofer, E., Natschlager, T., and Saminger-Platz, S. (2017). Central moment discrepancy (cmd) for domain-invariant rep­resentation learning. *arXiv preprint arXiv:1702.08811*. + +[Zhang et al., 2017a] Zhang, J., Li, W., and Ogunbona, P. (2017a). Joint geometrical and statistical alignment for visual domain adaptation. In *CVPR*. + +[Zhang et al., 2017b] Zhang, X., Zhuang, Y., Wang, W., and Pedrycz, W. (2017b). On­line feature transformation learning for cross-domain object category recognition. *IEEE transactions on neural networks and learning systems*. + +[Zhao and Hoi, 2010] Zhao, P. and Hoi, S. C. (2010). Otl: A framework of online transfer learning. In *Proceedings of the 27th international conference on machine learning (ICML- 10)*, pages 1231-1238. + +[Zhao et al., 2010] Zhao, Z., Chen, Y., Liu, J., and Liu, M. (2010). Cross-mobile elm based activity recognition. *International Journal of Engineering and Industries*, 1(1):30-38. + +[Zhao et al., 2011] Zhao, Z., Chen, Y., Liu, J., Shen, Z., and Liu, M. (2011). Cross-people mobile-phone based activity recognition. In *Proceedings of the Twenty-Second interna­tional joint conference on Artificial Intelligence (IJCAI)*, volume 11, pages 2545-2550. Citeseer. + +[Zheng et al., 2009] Zheng, V. W., Hu, D. H., and Yang, Q. (2009). Cross-domain activity recognition. In *Proceedings of the 11th international conference on Ubiquitous computing*, pages 61-70. ACM. + +[Zheng et al., 2008] Zheng, V. W., Pan, S. J., Yang, Q., and Pan, J. J. (2008). Transferring multi-device localization models using latent multi-task learning. In *AAAI*, volume 8, pages 1427-1432, Chicago, Illinois, USA. AAAI. + +[Zhuang et al., 2015] Zhuang, F., Cheng, X., Luo, P., Pan, S. J., and He, Q. (2015). Su­pervised representation learning: Transfer learning with deep autoencoders. In *IJCAI*,pages 4119-4125. + +[Zhuo et al., 2017] Zhuo, J., Wang, S., Zhang, W., and Huang, Q. (2017). Deep unsuper­vised convolutional domain adaptation. In *Proceedings of the 2017 ACM on Multimedia Conference*, pages 261-269. ACM. diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/modify_log.txt" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/modify_log.txt" deleted file mode 100644 index c5e0e582..00000000 --- "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/modify_log.txt" +++ /dev/null @@ -1,20 +0,0 @@ -该文件用来记录修改日志: -<----shw2018-2018-10-25----> -1. 新增章节markdown文件 - -<----shw2018-2018-10-28----> -1. 修改错误内容和格式 -2. 修改图片路径 - -<----shw2018-2018-10-31----> -1. 新增第九章文件夹,里面包括: -img---->用来放对应章节图片,例如路径./img/ch9/ch_* -readme.md---->章节维护贡献者信息 -modify_log---->用来记录修改日志 -第 * 章_xxx.md---->对应章节markdown文件 -第 * 章_xxx.pdf---->对应章节生成pdf文件,便于阅读 -其他---->待增加 -2. 修改readme内容 -3. 修改modify内容 -4. 修改章节内容,图片路径等 - diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/\347\254\254\345\215\201\344\270\200\347\253\240_\350\277\201\347\247\273\345\255\246\344\271\240.md" "b/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/\347\254\254\345\215\201\344\270\200\347\253\240_\350\277\201\347\247\273\345\255\246\344\271\240.md" deleted file mode 100644 index 0edeb8e3..00000000 --- "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/\347\254\254\345\215\201\344\270\200\347\253\240_\350\277\201\347\247\273\345\255\246\344\271\240.md" +++ /dev/null @@ -1,178 +0,0 @@ -[TOC] - -# 第十章 迁移学习 - -## 10.1 为什么需要迁移学习?(中科院计算所-王晋东) - -1. **大数据与少标注的矛盾**:虽然有大量的数据,但往往都是没有标注的,无法训练机器学习模型。人工进行数据标定太耗时。 -2. **大数据与弱计算的矛盾**:普通人无法拥有庞大的数据量与计算资源。因此需要借助于模型的迁移。 -3. **普适化模型与个性化需求的矛盾**:即使是在同一个任务上,一个模型也往往难以满足每个人的个性化需求,比如特定的隐私设置。这就需要在不同人之间做模型的适配。 -4. **特定应用(如冷启动)的需求**。 - -## 10.2 迁移学习的基本问题有哪些?(中科院计算所-王晋东) - -基本问题主要有3个: - -- **How to transfer**: 如何进行迁移学习?(设计迁移方法) -- **What to transfer**: 给定一个目标领域,如何找到相对应的源领域,然后进行迁移?(源领域选择) -- **When to transfer**: 什么时候可以进行迁移,什么时候不可以?(避免负迁移) - -## 10.3 迁移学习有哪些常用概念?(KeyFoece) - -- 基本定义 - - **域(Domain)**:数据特征和特征分布组成,是学习的主体 - - **源域 (Source domain)**:已有知识的域 - - **目标域 (Target domain)**:要进行学习的域 - - **任务 (Task)**:由目标函数和学习结果组成,是学习的结果 -- 按特征空间分类 - - **同构迁移学习(Homogeneous TL)**: 源域和目标域的特征空间相同,$D_s=D_t$ - - **异构迁移学习(Heterogeneous TL)**:源域和目标域的特征空间不同,$D_s\ne D_t$ -- 按迁移情景分类 - - **归纳式迁移学习(Inductive TL)**:源域和目标域的学习任务不同 - - **直推式迁移学习(Transductive TL)**:源域和目标域不同,学习任务相同 - - **无监督迁移学习(Unsupervised TL)**:源域和目标域均没有标签 -- 按迁移方法分类 - - **基于实例的迁移 (Instance based TL)**:通过权重重用源域和目标域的样例进行迁移 - - **基于特征的迁移 (Feature based TL)**:将源域和目标域的特征变换到相同空间 - - **基于模型的迁移 (Parameter based TL)**:利用源域和目标域的参数共享模型 - - **基于关系的迁移 (Relation based TL)**:利用源域中的逻辑网络关系进行迁移 - -![1542972502781](./img/ch11/1542972502781.png) - -![1542974131814](./img/ch11/1542974131814.png) - -## 10.4 迁移学习与传统机器学习有什么区别?(KeyFoece) - -| | 迁移学习 | 传统机器学习 | -| -------- | -------------------------- | -------------------- | -| 数据分布 | 训练和测试数据不需要同分布 | 训练和测试数据同分布 | -| 数据标签 | 不需要足够的数据标注 | 足够的数据标注 | -| 建模 | 可以重用之前的模型 | 每个任务分别建模 | - -![1542973960796](./img/ch11/1542973960796.png) - -## 10.5 迁移学习的基本思路?(中科院计算所-王晋东) - -**迁移学习的总体思路可以概括为**:开发算法来最大限度地利用有标注的领域的知识,来辅助目标领域的知识获取和学习。 - -**迁移学习的核心是**:找到源领域和目标领域之间的相似性,并加以合理利用。这种相似性非常普遍。比如,不同人的身体构造是相似的;自行车和摩托车的骑行方式是相似的;国际象棋和中国象棋是相似的;羽毛球和网球的打球方式是相似的。这种相似性也可以理解为不变量。以不变应万变,才能立于不败之地。 - -**有了这种相似性后,下一步工作就是, 如何度量和利用这种相似性。**度量工作的目标有两点:一是很好地度量两个领域的相似性,不仅定性地告诉我们它们是否相似,更定量地给出相似程度。二是以度量为准则,通过我们所要采用的学习手段,增大两个领域之间的相似性,从而完成迁移学习。 - -**一句话总结: 相似性是核心,度量准则是重要手段。** - -## 10.6 迁移学习与其他概念的区别(Limber) - -1. 迁移学习与多任务学习关系: - * **多任务学习**:多个相关任务一起协同学习; - * **迁移学习**:强调信息复用,从一个领域(domain)迁移到另一个领域。 -2. 迁移学习与领域自适应:**领域自适应**:使两个特征分布不一致的domain一致。 -3. 迁移学习与协方差漂移:**协方差漂移**:数据的条件概率分布发生变化。 - -## 10.7 什么是多任务学习? -在迁移学习中,从**任务A**里学习只是然后迁移到**任务B**。 -在多任务学习中,同时开始学习的,试图让**单个神经网络**同时做**几件事情**,然后希望这里每个任务都能帮到其他所有任务。 -> 指多个相关任务一起协同学习 - -## 10.8 多任务学习有什么意义? -1. 第一,如果你训练的一组任务,可以共用**低层次特征**。 -对于无人驾驶的例子,同时识别交通灯、汽车和行人是有道理的,这些物体有相似的特征,也许能帮你识别停车标志,因为这些都是道路上的特征。 -2. 第二,这个**准则没有那么绝对**,所以不一定是对的。 -但我从很多成功的多任务学习案例中看到,如果每个任务的数据量很接近,你还记得迁移学习时,你从任务学到知识然后迁移到任务,所以如果任务有**1百万个样本**,任务只有**1000个样本**,那么你从这**1百万个样本**学到的知识,真的可以帮你增强对更小数据集任务的训练。 -那么多任务学习又怎么样呢?在多任务学习中,你通常有更多任务而不仅仅是两个,所以也许你有,以前我们有**4个任务**,但比如说你要完成**100个任务**,而你要做多任务学习,尝试同时识别**100种不同类型的物体**。你可能会发现,每个任务大概有**1000个样本**。 -所以如果你专注加强单个任务的性能,比如我们专注加强第**100个任务**的表现,我们用表示,如果你试图单独去做这个最后的任务,你只有**1000个样本**去训练这个任务,这是**100项任务**之一,而通过在**其他99项任务**的训练,这些加起来可以一共有**99000个样本**,这可能大幅提升算法性能,可以提供很多知识来增强这个任务的性能。 -不然对于任务,只有**1000个样本**的训练集,效果可能会很差。如果有对称性,这**其他99个任务**,也许能提供一些数据或提供一些知识来帮到这**100个任务中**的每一个任务。所以第二点不是绝对正确的准则,但我通常会看的是如果你专注于单项任务,如果想要从多任务学习得到很大性能提升,那么其他任务加起来必须要有比单个任务大得多的数据量。 -要满足这个条件,其中一种方法是,比如右边这个例子这样,或者如果每个任务中的数据量很相近,但关键在于, 如果对于单个任务你已经有**1000个样本**了,那么对于所有其他任务,你最好有超过**1000个样 本**,这样其他任务的知识才能帮你改善这个任务的性能。 -3. 最后多任务学习往往在以下场合**更有意义**,当你可以训练一个足够大的神经网络,同时做好所有的工作,所以多任务学习的**替代方法**是为每个任务**训练一个单独的神经网络**。 -所以不是训练单个神经网络同时处理行人、汽车、停车标志和交通灯检测。你可以训练一个**用于行人检测的神经网络**,一个**用于汽车检测的神经网络**,一个**用于停车标志检测的神经网络**和一个**用于交通信号灯检测的神经网络**。 -那么研究员 Rich Carona 几年前发现的是什么呢? -多任务学习会降低性能的唯一情况,和训练单个神经网络相比性能更低的情况就是你的神经网络还不够大。 但如果你可以训练一个足够大的神经网络,那么多任务学习肯定**不会或者很少**会**降低性能**,我们都希望它可以提升性能,比单独训练神经网络来单独完成各个任务**性能要更好**。 -4. 所以**这就是多任务学习**,在实践中,多任务学习的使用频率要低于迁移学习。 -我看到很多迁移学习的应用,你需要解决一个问题,但你的**训练数据很少**,所以你需要找一个数据很多的相关问题来**预先学习**,并将知识迁移到这个新问题上。 -但多任务学习比较少见,就是你需要同时处理很多任务,都要做好,你可以同时训练所有这些任务,也许计算机视觉是一个例子。 -在物体检测中,我们看到**更多**使用多任务学习的应用,其中一个神经网络尝试检测一大堆物体,比分别训练不同的神经网络检测物体**更好**。但我说,平均来说,目前迁移学习使用频率**更高**,比多任务学习频率**更高**,但两者都可以成为你的**强力工具**。 -5. 总结一下,多任务学习能让你训练一个神经网络来执行许多任务,这可以给你更高的性能,比单独完成各个任务更高的性能。 -但要**注意**,**实际上**迁移学习比多任务学习使用频率**更高**。 -我看到很多任务都是,如果你想解决一个机器学习问题,但你的数据集相对较小,那么迁移学习真的能帮到你,就是如果你找到一个相关问题,其中数据量要大得多,你就能以它为基础训练你的神经网络,然后迁移到这个数据量很少的任务上来。 -6. 今天我们学到了很多和迁移学习有关的问题,还有一些迁移学习和多任务学习的应用。 -但多任务学习,我觉得使用频率比迁移学习要少得多,也许其中一个例外是计算机视觉,物体检测。在那些任务中,人们经常训练一个神经网络同时检测很多不同物体,这比训练单独的神经网络来检测视觉物体要更好。但平均而言,我认为即使迁移学习和多任务学习工作方式类似。 实际上,我看到用迁移学习比多任务学习要更多,我觉得这是因为你很难找到那么多相似且数据量对等的任务可以用单一神经网络训练。 -再次,在计算机视觉领域,物体检测这个例子是最显著的例外情况。 -7. 所以这就是多任务学习,多任务学习和迁移学习都是你的工具包中的重要工具。 -最后,我想继续讨论端到端深度学习,所以我们来看下一个视频来讨论端到端学习。 - -## 10.9 什么是端到端的深度学习? -1. 深度学习中**最令人振奋**的最新动态之一就是端到端深度学习的兴起,那么端到端学习到底是什么呢?简而言之,以前有一些数据处理系统或者学习系统,它们需要多个阶段的处理。 -那么端到端深度学习就是**忽略所有这些不同的阶段**,用单个神经网络代替它。 -2. 而端到端深度学习就只需要把训练集拿过来,直接学到了和之间的函数映射,直接绕过了其中很多步骤。对一些学科里的人来说,这点相当难以接受,他们无法接受这样**构建AI系统**,因为有些情况,**端到端方法**完全**取代**了旧系统,某些投入了多年研究的中间组件也许已经**过时**了。 - -## 10.10 端到端的深度学习举例? -1. 这张图上是一个研究员做的人脸识别门禁,是百度的林元庆研究员做的。 -这是一个相机,它会拍下接近门禁的人,如果它认出了那个人,门禁系统就自动打开,让他通过,所以你不需要刷一个**RFID工卡**就能进入这个设施。 -系统部署在越来越多的中国办公室,希望在其他国家也可以部署更多,你可以接近门禁,如果它认出你的脸,它就直接让你通过,你不需要带RFID工卡。 -2. 我们再来看几个例子,比如机器翻译。 -传统上,机器翻译系统也有一个很复杂的流水线,比如英语机翻得到文本,然后做文本分析,基本上要从文本中提取一些特征之类的,经过很多步骤,你最后会将英文文本翻译成法文。 -因为对于机器翻译来说的确有很多(英文,法文)的数据对,端到端深度学习在机器翻译领域非常好用,那是因为在今天可以收集对的大数据集,就是英文句子和对应的法语翻译。 -所以在这个例子中,端到端深度学习效果很好。 - -## 10.11 端到端的深度学习有什么挑战? -1. 事实证明,端到端深度学习的挑战之一是,你可能需要大量数据才能让系统表现良好,比如,你只有**3000小时数据**去训练你的**语音识别系统**,那么传统的流水线效果真的很好。 -但当你拥有非常大的数据集时,比如**10,000小时数据**或者**100,000小时**数据,这样端到端方法突然开始很厉害了。所以当你的**数据集较小**的时候,传统流水线方法其实效果也不错,通常做得**更好**。 -2. 你需要**大数据集**才能让**端到端方法**真正发出耀眼光芒。如果你的数据量适中,那么也可以用中间件方法,你可能输入还是音频,然后绕过特征提取,直接尝试从神经网络输出音位,然后也可以在其他阶段用,所以这是往端到端学习迈出的一小步,但还没有到那里。 - -## 10.13 端到端的深度学习优缺点? -假设你正在搭建一个机器学习系统,你要决定是否使用端对端方法,我们来看看端到端深度学习的一些优缺点,这样你就可以根据一些准则,判断你的应用程序是否有希望使用端到端方法。 - -这里是应用端到端学习的一些优点: -1. 首先端到端学习真的只是让数据说话。所以如果你有足够多的数据,那么不管从 x 到 y 最适合的函数映射是什么,如果你训练一个足够大的神经网 络,希望这个神经网络能自己搞清楚,而使用纯机器学习方法,直接从到输入去训练的神经网 络,可能更能够捕获数据中的任何统计信息,而不是被迫引入人类的成见。 -例如,在语音识别领域,早期的识别系统有这个音位概念,就是基本的声音单元,如 cat 单词的“cat”的 Cu-、Ah-和 Tu-,我觉得这个音位是人类语言学家生造出来的,我实际上认为音位其实是语音学家的幻想,用音位描述语言也还算合理。但是不要强迫你的学习算法以音位为单位思考,这点有时没那么明显。如果你让你的学习算法学习它想学习的任意表示方式,而不是强迫你的学习算法使用音位作为表示方式,那么其整体表现可能会更好。 -2. 端到端深度学习的第二个好处就是这样,所需手工设计的组件更少,所以这也许能够简化你的设计工作流程,你不需要花太多时间去手工设计功能,手工设计这些中间表示方式。 - -这里是应用端到端学习的一些缺点: -1. 首先,它可能需要大量的数据。要直接学到这个到的映射,你可能需要大量数据。 -我们在以前的视频里看过一个例子,其中你可以收集大量子任务数据。 -比如人脸识别,我们可以收集很多数据用来分辨图像中的人脸,当你找到一张脸后,也可以找得到很多人脸识别数据。 -但是对于整个端到端任务,可能只有更少的数据可用。所以这是端到端学习的输入端,是输出端,所以你需要很多这样的数据,在输入端和输出端都有数据,这样可以训练这些系统。 -这就是为什么我们称之为端到端学习,因为你直接学习出从系统的一端到 系统的另一端。 -2. 另一个缺点是,它排除了可能有用的手工设计组件。 -机器学习研究人员一般都很鄙视手工设计的东西,但如果你没有很多数据,你的学习算法就没办法从很小的训练集数据中获得洞察力。 -所以手工设计组件在这种情况,可能是把人类知识直接注入算法的途径,这总不是一件坏事。 -我觉得学习算法有两个主要的知识来源,一个是数据,另一个是你手工设计的任何东西,可能是组件,功能,或者其他东西。 -所以当你有大量数据时,手工设计的东西就不太重要了,但是当你没有太多的数据时,构造一个精心设计的系统,实际上可以将人类对这个问题的很多 认识直接注入到问题里,进入算法里应该挺有帮助的。 - -总结: -1. 所以端到端深度学习的弊端之一是它把可能有用的人工设计的组件排除在外了,精心设计的人工组件可能非常有用,但它们也有可能真的伤害到你的算法表现。 -例如,强制你的算法以音位为单位思考,也许让算法自己找到更好的表示方法更好。 -所以这是一把双刃剑,可能有坏处,可能有好处,但往往好处更多,手工设计的组件往往在训练集更小的时候帮助更大。 - -## 10.14 什么是负迁移?产生负迁移的原因有哪些?(中科院计算所-王晋东) - -负迁移(Negative Transfer)指的是,在源域上学习到的知识,对于目标域上的学习产生负面作用。 - -产生负迁移的原因主要有: -- 数据问题:源域和目标域压根不相似,谈何迁移? -- 方法问题:源域和目标域是相似的,但是,迁移学习方法不够好,没找到可迁移的成分。 - -负迁移给迁移学习的研究和应用带来了负面影响。在实际应用中,找到合理的相似性,并且选择或开发合理的迁移学习方法,能够避免负迁移现象。 - -## 10.15 什么是迁移学习? - -1. 找到目标问题的相似性,迁移学习任务就是从相似性出发,将旧领域(domain)学习过的模型应用在新领域上。 -2. 迁移学习,是指利用数据、任务、或模型之间的相似性,将在旧领域学习过的模型,应用于新领域的一种学习过程。 -3. 迁移学习**最有用的场合**是,如果你尝试优化任务B的性能,通常这个任务数据相对较少。 - 例如,在放射科中你知道很难收集很多射线扫描图来搭建一个性能良好的放射科诊断系统,所以在这种情况下,你可能会找一个相关但不同的任务,如图像识别,其中你可能用 1 百万张图片训练过了,并从中学到很多低层次特征,所以那也许能帮助网络在任务在放射科任务上做得更好,尽管任务没有这么多数据。 -4. 迁移学习什么时候是有意义的?它确实可以**显著提高**你的**学习任务的性能**,但我有时候也见过有些场合使用迁移学习时,任务实际上数据量比任务要少, 这种情况下增益可能不多。 - -> 什么情况下可以使用迁移学习? -> -> 假如两个领域之间的区别特别的大,**不可以直接采用迁移学习**,因为在这种情况下效果不是很好。在这种情况下,推荐使用[3]的工作,在两个相似度很低的domain之间一步步迁移过去(踩着石头过河)。 - -> 1. 迁移学习主要解决方案有哪些? -> 2. 除直接看infer的结果的Accurancy以外,如何衡量迁移学习学习效果? -> 3. 对抗网络是如何进行迁移的? - -Reference: - -1. [王晋东,迁移学习简明手册](https://github.com/jindongwang/transferlearning-tutorial) -2. Ben-David, S., Blitzer, J., Crammer, K., Kulesza, A., Pereira, F., & Vaughan, J. W. (2010). A theory of learning from different domains. Machine learning, 79(1-2), 151-175. -3. Tan, B., Song, Y., Zhong, E. and Yang, Q., 2015, August. Transitive transfer learning. In Proceedings of the 21th ACM SIGKDD International Conference on Knowledge Discovery and Data Mining (pp. 1155-1164). ACM. - diff --git "a/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_15_1.png" "b/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_15_1.png" similarity index 100% rename from "ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_15_1.png" rename to "ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_15_1.png" diff --git "a/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_15_2.png" "b/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_15_2.png" similarity index 100% rename from "ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_15_2.png" rename to "ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_15_2.png" diff --git "a/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_18_1.png" "b/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_18_1.png" new file mode 100644 index 00000000..5d53edc7 Binary files /dev/null and "b/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_18_1.png" differ diff --git "a/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_19_1.png" "b/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_19_1.png" new file mode 100644 index 00000000..0ada3972 Binary files /dev/null and "b/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_19_1.png" differ diff --git "a/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_36_1.png" "b/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_36_1.png" similarity index 100% rename from "ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_36_1.png" rename to "ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_36_1.png" diff --git "a/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_43_1.png" "b/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_43_1.png" similarity index 100% rename from "ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_43_1.png" rename to "ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_43_1.png" diff --git "a/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_43_2.png" "b/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_43_2.png" similarity index 100% rename from "ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_43_2.png" rename to "ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_43_2.png" diff --git "a/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_43_3.png" "b/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_43_3.png" similarity index 100% rename from "ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_43_3.png" rename to "ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_43_3.png" diff --git "a/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_43_4.png" "b/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_43_4.png" similarity index 100% rename from "ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_43_4.png" rename to "ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_43_4.png" diff --git "a/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_43_5.png" "b/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_43_5.png" similarity index 100% rename from "ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_43_5.png" rename to "ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_43_5.png" diff --git "a/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_43_6.png" "b/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_43_6.png" similarity index 100% rename from "ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_43_6.png" rename to "ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_43_6.png" diff --git "a/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_43_7.png" "b/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_43_7.png" similarity index 100% rename from "ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_43_7.png" rename to "ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_43_7.png" diff --git "a/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_43_8.png" "b/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_43_8.png" similarity index 100% rename from "ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_43_8.png" rename to "ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_43_8.png" diff --git "a/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_4_1.png" "b/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_4_1.png" similarity index 100% rename from "ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_4_1.png" rename to "ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_4_1.png" diff --git "a/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_7_1.png" "b/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_7_1.png" similarity index 100% rename from "ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_7_1.png" rename to "ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_7_1.png" diff --git "a/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/modify_log.txt" "b/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/modify_log.txt" similarity index 100% rename from "ch13_\344\274\230\345\214\226\347\256\227\346\263\225/modify_log.txt" rename to "ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/modify_log.txt" diff --git "a/ch11_\350\277\201\347\247\273\345\255\246\344\271\240/readme.md" "b/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/readme.md" similarity index 100% rename from "ch11_\350\277\201\347\247\273\345\255\246\344\271\240/readme.md" rename to "ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/readme.md" diff --git "a/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/\347\254\254\345\215\201\344\270\211\347\253\240_\344\274\230\345\214\226\347\256\227\346\263\225.md" "b/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/\347\254\254\345\215\201\344\270\211\347\253\240_\344\274\230\345\214\226\347\256\227\346\263\225.md" similarity index 60% rename from "ch13_\344\274\230\345\214\226\347\256\227\346\263\225/\347\254\254\345\215\201\344\270\211\347\253\240_\344\274\230\345\214\226\347\256\227\346\263\225.md" rename to "ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/\347\254\254\345\215\201\344\270\211\347\253\240_\344\274\230\345\214\226\347\256\227\346\263\225.md" index 88eae7fd..a71a8593 100644 --- "a/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/\347\254\254\345\215\201\344\270\211\347\253\240_\344\274\230\345\214\226\347\256\227\346\263\225.md" +++ "b/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/\347\254\254\345\215\201\344\270\211\347\253\240_\344\274\230\345\214\226\347\256\227\346\263\225.md" @@ -4,222 +4,102 @@ # 第一十三章 优化算法 +## 13.1 如何解决训练样本少的问题 -## 13.1 CPU 和 GPU 的区别? - -   -**概念:** +目前大部分的深度学习模型仍然需要海量的数据支持。例如 ImageNet 数据就拥有1400多万的图片。而现实生产环境中,数据集通常较小,只有几万甚至几百个样本。这时候,如何在这种情况下应用深度学习呢? +(1)利用预训练模型进行迁移微调(fine-tuning),预训练模型通常在特征上拥有很好的语义表达。此时,只需将模型在小数据集上进行微调就能取得不错的效果。这也是目前大部分小数据集常用的训练方式。视觉领域内,通常会ImageNet上训练完成的模型。自然语言处理领域,也有BERT模型等预训练模型可以使用。    -CPU 全称是 central processing unit,CPU 是一块超大规模的集成电路,是一台计算机的运 算和控制核心,它的主要功能是解释计算机指令和处理计算机软件中的数据。 +(2)单样本或者少样本学习(one-shot,few-shot learning),这种方式适用于样本类别远远大于样本数量的情况等极端数据集。例如有1000个类别,每个类别只提供1-5个样本。少样本学习同样也需要借助预训练模型,但有别于微调的在于,微调通常仍然在学习不同类别的语义,而少样本学习通常需要学习样本之间的距离度量。例如孪生网络(Siamese Neural Networks)就是通过训练两个同种结构的网络来判别输入的两张图片是否属于同一类。 +​ 上述两种是常用训练小样本数据集的方式。此外,也有些常用的手段,例如数据集增强、正则或者半监督学习等方式来解决小样本数据集的训练问题。 -   -GPU 全称是 graphics processing unit,GPU 是将计算机系统,所需要的显示信息进行转换 的驱动,并向显示器提供扫描信号,控制显示器的正确显示,是连接显示器和个人电脑主板的 重要元件,是人机对话的重要设备之一。 +## 13.2 深度学习是否能胜任所有数据集? -   -**缓存:** -   -CPU 有大量的缓存结构,目前主流的 CPU 芯片上都有四级缓存,这些缓存结构消耗了大 量的晶体管,在运行的时候需要大量的电力。反观 GPU 的缓存就很简单,目前主流的 GPU 芯 片最多有两层缓存。CPU 消耗在晶体管上的空间和能耗,GPU 都可以用来做成 ALU 单元,也 因此 GPU 比 CPU 的效率要高一些。 +深度学习并不能胜任目前所有的数据环境,以下列举两种情况: -   -**响应方式:** -   -对 CPU 来说,要求的是实时响应,对单任务的速度要求很高,所以就要用很多层缓存的 办法来保证单任务的速度。对 GPU 来说大家不关心第一个像素什么时候计算完成,而是都关 心最后一个像素什么时候计算出来,所以 GPU 就把所有的任务都排好,然后再批处理,这样 对缓存的要求就很低了。举个不恰当的例子,在点击 10 次鼠标的时候,CPU 要每一次点击都 要及时响应,而 GPU 会等第 10 次点击后,再一次性批处理响应。 +(1)深度学习能取得目前的成果,很大一部分原因依赖于海量的数据集以及高性能密集计算硬件。因此,当数据集过小时,需要考虑与传统机器学习相比,是否在性能和硬件资源效率更具有优势。 +(2)深度学习目前在视觉,自然语言处理等领域都有取得不错的成果。这些领域最大的特点就是具有局部相关性。例如图像中,人的耳朵位于两侧,鼻子位于两眼之间,文本中单词组成句子。这些都是具有局部相关性的,一旦被打乱则会破坏语义或者有不同的语义。所以当数据不具备这种相关性的时候,深度学习就很难取得效果。 -   -**浮点运算:** -   -CPU 除了负责浮点整形运算外,还有很多其他的指令集的负载,比如像多媒体解码,硬 件解码等,所以 CPU 是个多才多艺的东西,而 GPU 基本上就是只做浮点运算的,也正是因为 只做浮点运算,所以设计结构简单,也就可以做的更快。另外显卡的 GPU 和单纯为了跑浮点 高性能运算的 GPU 还是不太一样,显卡的 GPU 还要考虑配合图形输出显示等方面,而有些专 用 GPU 设备,就是一个 PCI 卡上面有一个性能很强的浮点运算 GPU,没有显示输出的,这样 的 GPU 就是为了加快某些程序的浮点计算能力。CPU 注重的是单线程的性能,也就是延迟, 对于 CPU 来说,要保证指令流不中断,所以 CPU 需要消耗更多的晶体管和能耗用在控制部分, 于是CPU分配在浮点计算的功耗就会变少。GPU注重的是吞吐量,单指令能驱动更多的计算, 所以相比较而言 GPU 消耗在控制部分的能耗就比较少,因此也就可以把电省下来的资源给浮 点计算使用。 +## 13.3 有没有可能找到比已知算法更好的算法? -   -**应用方向:** -   -像操作系统这一类应用,需要快速响应实时信息,需要针对延迟优化,所以晶体管数量和能耗都需要用在分支预测,乱序执行上,低延迟缓存等控制部分,而这都是 CPU 的所擅长的。 对于像矩阵一类的运算,具有极高的可预测性和大量相似运算的,这种高延迟,高吞吐的架构 运算,就非常适合 GPU。 +在最优化理论发展中,有个没有免费午餐的定律,其主要含义在于,在不考虑具体背景和细节的情况下,任何算法和随机猜的效果期望是一样的。即,没有任何一种算法能优于其他一切算法,甚至不比随机猜好。深度学习作为机器学习领域的一个分支同样符合这个定律。所以,虽然目前深度学习取得了非常不错的成果,但是我们同样不能盲目崇拜。 -   -**浅显解释:** -   -一块 CPU 相当于一个数学教授,一块 GPU 相当于 100 个小学生。 -   -第一回合,四则运算,一百个题。教授拿到卷子一道道计算。100 个小学生各拿一道题。 教授刚开始计算到第二题的时候,小学生就集体交卷了。 -   -第二回合,高等函数,一百个题。当教授搞定后。一百个小学生可能还不知道该做些什么。 -   -这两个回合就是 CPU 和 GPU 的区别了。 +优化算法本质上是在寻找和探索更符合数据集和问题的算法,这里数据集是算法的驱动力,而需要通过数据集解决的问题就是算法的核心,任何算法脱离了数据都会没有实际价值,任何算法的假设都不能脱离实际问题。因此,实际应用中,面对不同的场景和不同的问题,可以从多个角度针对问题进行分析,寻找更优的算法。 -## 13.2 如何解决训练样本少的问题 +## 13.4 什么是共线性,如何判断和解决共线性问题? -   -要训练一个好的 CNN 模型,通常需要很多训练数据,尤其是模型结构比较复杂的时候, 比如 ImageNet 数据集上训练的模型。虽然深度学习在 ImageNet 上取得了巨大成功,但是一个 现实的问题是,很多应用的训练集是较小的,如何在这种情况下应用深度学习呢?有三种方法 可供读者参考。 +对于回归算法,无论是一般回归还是逻辑回归,在使用多个变量进行预测分析时,都可能存在多变量相关的情况,这就是多重共线性。共线性的存在,使得特征之间存在冗余,导致过拟合。 -   -(1)可以将 ImageNet 上训练得到的模型做为起点,利用目标训练集和反向传播对其进 行继续训练,将模型适应到特定的应用。ImageNet 起到预训练的作用。 -   -(2)如果目标训练集不够大,也可以将低层的网络参数固定,沿用 ImageNet 上的训练集 结果,只对上层进行更新。这是因为底层的网络参数是最难更新的,而从 ImageNet 学习得到 的底层滤波器往往描述了各种不同的局部边缘和纹理信息,而这些滤波器对一般的图像有较好 的普适性。 -   -(3)直接采用 ImageNet 上训练得到的模型,把最高的隐含层的输出作为特征表达,代 替常用的手工设计的特征。 +常用判断是否存在共线性的方法有: -## 13.3 什么样的样本集不适合用深度学习? +(1)相关性分析。当相关性系数高于0.8,表明存在多重共线性;但相关系数低,并不能表示不存在多重共线性; -   -(1)数据集太小,数据样本不足时,深度学习相对其它机器学习算法,没有明显优势。 -   -(2)数据集没有局部相关特性,目前深度学习表现比较好的领域主要是图像/语音 /自然语言处理等领域,这些领域的一个共性是局部相关性。图像中像素组成物体,语音 信号中音位组合成单词,文本数据中单词组合成句子,这些特征元素的组合一旦被打乱, 表示的含义同时也被改变。对于没有这样的局部相关性的数据集,不适于使用深度学习算 法进行处理。举个例子:预测一个人的健康状况,相关的参数会有年龄、职业、收入、家 庭状况等各种元素,将这些元素打乱,并不会影响相关的结果。 +(2)方差膨胀因子VIF。当VIF大于5或10时,代表模型存在严重的共线性问题; -## 13.4 有没有可能找到比已知算法更好的算法? +(3)条件系数检验。 当条件数大于100、1000时,代表模型存在严重的共线性问题。 +通常可通过PCA降维、逐步回归法和LASSO回归等方法消除共线性。 +## 13.5 权值初始化方法有哪些? -   -没有免费的午餐定理: -![没有免费的午餐定理](./img/ch13/figure_13_4_1.png) -
图 13.4 没有免费的午餐(黑点:训练样本;白点:测试样本)
+在深度学习的模型中,从零开始训练时,权重的初始化有时候会对模型训练产生较大的影响。良好的初始化能让模型快速、有效的收敛,而糟糕的初始化会使得模型无法训练。 -   -对于训练样本(黑点),不同的算法 A/B 在不同的测试样本(白点)中有不同的表现,这表示:对于一个学习算法A,若它在某些问题上比学习算法B更好,则必然存在一些问题, 在那里B比A好。 -   -也就是说:对于所有问题,无论学习算法 A 多聪明,学习算法 B 多笨拙,它们的期望性 能相同。 -   -但是:没有免费午餐定力假设所有问题出现几率相同,实际应用中,不同的场景,会有不 同的问题分布,所以,在优化算法时,针对具体问题进行分析,是算法优化的核心所在。 +目前,大部分深度学习框架都提供了各类初始化方式,其中一般常用的会有如下几种: +**1. 常数初始化(constant)** -## 13.5 何为共线性, 跟过拟合有啥关联? +​ 把权值或者偏置初始化为一个常数。例如设置为0,偏置初始化为0较为常见,权重很少会初始化为0。TensorFlow中也有zeros_initializer、ones_initializer等特殊常数初始化函数。 -   -共线性:多变量线性回归中,变量之间由于存在高度相关关系而使回归估计不准确。 -   -产生问题:共线性会造成冗余,导致过拟合。 -   -解决方法:排除变量的相关性、加入权重正则。 - -## 13.6 广义线性模型是怎被应用在深度学习中? +**2. 高斯初始化(gaussian)** -   -深度学习从统计学角度,可以看做递归的广义线性模型。 -   -广义线性模型相对于经典的线性模型$(y=wx+b)$,核心在于引入了连接函数 $g(\cdot)$,形式变为: $y=g-1(wx+b)$。 -   -深度学习时递归的广义线性模型,神经元的激活函数,即为广义线性模型的链接函数。逻 辑回归(广义线性模型的一种)的 Logistic 函数即为神经元激活函数中的 Sigmoid 函数,很多 类似的方法在统计学和神经网络中的名称不一样,容易引起困惑。 - -## 13.7 造成梯度消失的原因? - - - -   -神经网络的训练中,通过改变神经元的权重,使网络的输出值尽可能逼近标签以降低误差 值,训练普遍使用 BP 算法,核心思想是,计算出输出与标签间的损失函数值,然后计算其相 对于每个神经元的梯度,进行权值的迭代。 -   -梯度消失会造成权值更新缓慢,模型训练难度增加。造成梯度消失的一个原因是,许多激 活函数将输出值挤压在很小的区间内,在激活函数两端较大范围的定义域内梯度为 $0$。造成学 习停止。 -![sigmoid 函数与其导数](./img/ch13/figure_13_7_1.png) -
图 13.7 sigmoid 函数的梯度消失
- -## 13.8 权值初始化方法有哪些? - -   -权值初始化的方法主要有:常量初始化(constant)、高斯分布初始化(gaussian)、 positive_unitball 初始化、均匀分布初始化(uniform)、xavier 初始化、msra 初始化、双线性初 始化(bilinear)。 - -   -**1. 常量初始化(constant)** -   -把权值或者偏置初始化为一个常数,具体是什么常数,可以自己定义。 - -   -**2. 高斯分布初始化(gaussian)** -   -需要给定高斯函数的均值与标准差。 - -   -**3. positive_unitball 初始化** -   -让每一个神经元的输入的权值和为 $1$,例如:一个神经元有 $100$ 个输入,让这 $100$ 个输入 -的权值和为 $1$. 首先给这 $100$ 个权值赋值为在$(0,1)$之间的均匀分布,然后,每一个权值再 除以它们的和就可以啦。这么做,可以有助于防止权值初始化过大,从而防止激活函数(sigmoid 函数)进入饱和区。所以,它应该比较适合 simgmoid 形的激活函数。 +​ 给定一组均值和标准差,随机初始化的参数会满足给定均值和标准差的高斯分布。高斯初始化是很常用的初始化方式。特殊地,在TensorFlow中还有一种截断高斯分布初始化(truncated_normal_initializer),其主要为了将超过两个标准差的随机数重新随机,使得随机数更稳定。 -   -**4. 均匀分布初始化(uniform)** -   -将权值与偏置进行均匀分布的初始化,用 min 与 max 控制它们的的上下限,默认为$(0,1)$。 +**3. 均匀分布初始化(uniform)** -   -**5. xavier 初始化** -   -对于权值的分布:均值为 $0$,方差为($1$ / 输入的个数)的均匀分布。如果我们更注重前 -向传播的话,我们可以选择 fan_in,即正向传播的输入个数;如果更注重后向传播的话,我们选择 fan_out, 因为在反向传播的时候,fan_out 就是神经元的输入个数;如果两者都考虑的话, 就选 average = (fan_in + fan_out) /$2$。对于 ReLU 激活函数来说,XavierFiller 初始化也是很适合。关于该初始化方法,具体可以参考文章1、文章2,该方法假定激活函数是线性的。 +​ 给定最大最小的上下限,参数会在该范围内以均匀分布方式进行初始化,常用上下限为(0,1)。 -   -**6. msra 初始化** -   -对于权值的分布:基于均值为 $0$,方差为( $2$/输入的个数)的高斯分布;它特别适合 ReLU 激活函数,该方法主要是基于 Relu 函数提出的,推导过程类似于 xavier。 +**4. xavier 初始化(uniform)** -   -**7. 双线性初始化(bilinear)** -   -常用在反卷积神经网络里的权值初始化。 +​ 在batchnorm还未出现之前,要训练较深的网络,防止梯度弥散,需要依赖非常好的初始化方式。xavier 就是一种比较优秀的初始化方式,也是目前最常用的初始化方式之一。其目的是为了使得模型各层的激活值和梯度在传播过程中的方差保持一致。本质上xavier 还是属于均匀分布初始化,但与上述的均匀分布初始化有所不同,xavier 的上下限将在如下范围内进行均匀分布采样: +$$ +[-\sqrt{\frac{6}{n+m}},\sqrt{\frac{6}{n+m}}] +$$ +​ 其中,n为所在层的输入维度,m为所在层的输出维度。 -## 13.9 启发式优化算法中,如何避免陷入局部最优解? +**6. kaiming初始化(msra 初始化)** -   -启发式算法中,局部最优值的陷入无法避免。启发式,本质上是一种贪心策略,这也在客 观上决定了不符合贪心规则的更好(或者最优)解会错过。 -   -简单来说,避免陷入局部最优就是两个字:随机。 -   -具体实现手段上,可以根据所采用的启发式框架来灵活地加入随机性。比如遗传里面,可 以在交叉变异时,可以在控制人口策略中,也可以在选择父本母本样本时;禁忌里面,可以在 禁忌表的长度上体现,也可以在解禁策略中使用,等等。这些都要结合具体问题特定的算例集, 需要反复尝试摸索才行。参数的敏感性是一个问题,建议不要超过 $3$ 个参数,参数越不敏感越好。不同算例集用不同种子运行多次($100$ 次左右才有统计意义),统计平均性能即可。需注 意全局的随机重启通常来说不是一个好办法,因为等于主动放弃之前搜索结果,万不得已不要 用,或者就是不用。 +​ kaiming初始化,在caffe中也叫msra 初始化。kaiming初始化和xavier 一样都是为了防止梯度弥散而使用的初始化方式。kaiming初始化的出现是因为xavier存在一个不成立的假设。xavier在推导中假设激活函数都是线性的,而在深度学习中常用的ReLu等都是非线性的激活函数。而kaiming初始化本质上是高斯分布初始化,与上述高斯分布初始化有所不同,其是个满足均值为0,方差为2/n的高斯分布: +$$ +[0,\sqrt{\frac{2}{n}}] +$$ +​ 其中,n为所在层的输入维度。 -   -**三个原则应该把握:越随机越好;越不随机越好;二者平衡最好。** +除上述常见的初始化方式以外,不同深度学习框架下也会有不同的初始化方式,读者可自行查阅官方文档。 -   -**1. 越随机越好** -   -没有随机性,一定会陷入局部最优。为了获得更大的找到最优解的期望,算法中一定要有 -足够的随机性。具体体现为鲁棒性较好,搜索时多样性较好。算法的每一步选择都可以考虑加入随机性,但要控制好概率。比如,某个贪心策略下,是以概率 $1 $做某一动作,可以考虑将其 改为以概率 $0.999$ 做之前的操作,以剩余概率做其他操作。具体参数设置需调试。 +## 13.5 如何防止梯度下降陷入局部最优解? -   -**2. 越不随机越好** -   -随机性往往是对问题内在规律的一种妥协。即没有找到其内在规律,又不知道如何是好, 为了获得更好的多样性,逼不得已加入随机。因此,对给定问题的深入研究才是根本:分辨出 哪些时候,某个动作就是客观上能严格保证最优的——这点至关重要,直接决定了算法性能。 最好的算法一定是和问题结构紧密相连的,范范地套用某个启发式的框架不会有出色的性能。 当然,如果不是追求性能至上,而是考虑到开发效率实现成本这些额外因素,则另当别论。 +梯度下降法(GD)及其一些变种算法是目前深度学习里最常用于求解凸优化问题的优化算法。神经网络很可能存在很多局部最优解,而非全局最优解。 为了防止陷入局部最优,通常会采用如下一些方法,当然,这并不能保证一定能找到全局最优解,或许能得到一个比目前更优的局部最优解也是不错的: -   -**3. 二者平衡最好** -   -通常情况下,做好第一点,可以略微改善算法性能;做好第二点,有希望给算法带来质的提高。而二者调和后的平衡则会带来质的飞跃。 +**(1)stochastic GD** /**Mini-Batch GD** -   -贪心是“自强不息”的精进,不放过任何改进算法的机会;多样性的随机是“厚德载物”的一分包 容,给那些目前看似不那么好的解一些机会。调和好二者,不偏颇任何一方才能使算法有出色 的性能。要把握这种平衡,非一朝一夕之功,只能在反复试验反思中去细细品味。 -   -要结合具体问题而言,范范空谈无太大用。 +​ 在GD算法中,每次的梯度都是从所有样本中累计获取的,这种情况最容易导致梯度方向过于稳定一致,且更新次数过少,容易陷入局部最优。而stochastic GD是GD的另一种极端更新方式,其每次都只使用一个样本进行参数更新,这样更新次数大大增加也就不容易陷入局部最优。但引出的一个问题的在于其更新方向过多,导致不易于进一步优化。Mini-Batch GD便是两种极端的折中,即每次更新使用一小批样本进行参数更新。Mini-Batch GD是目前最常用的优化算法,严格意义上Mini-Batch GD也叫做stochastic GD,所以很多深度学习框架上都叫做SGD。 +**(2)动量 ** +​ 动量也是GD中常用的方式之一,SGD的更新方式虽然有效,但每次只依赖于当前批样本的梯度方向,这样的梯度方向依然很可能很随机。动量就是用来减少随机,增加稳定性。其思想是模仿物理学的动量方式,每次更新前加入部分上一次的梯度量,这样整个梯度方向就不容易过于随机。一些常见情况时,如上次梯度过大,导致进入局部最小点时,下一次更新能很容易借助上次的大梯度跳出局部最小点。 -## 13.10 凸优化中如何改进 GD 方法以防止陷入局部最优解? +**(3)自适应学习率 ** -   -在对函数进行凸优化时,如果使用导数的方法(如:梯度下降法/GD,牛顿法等)来寻找最优解,有可能陷入到局部最优解而非全局最优解。 -   -为了防止得到局部最优,可以对梯度下降法进行一些改进,防止陷入局部最优。 -   -但是请注意,这些方法只能保证以最大的可能找到全局最优,无法保证 $100\%$得到全局最优。 +​ 无论是GD还是动量重点优化角度是梯度方向。而学习率则是用来直接控制梯度更新幅度的超参数。自适应学习率的优化方法有很多,例如Adagrad和RMSprop。两种自适应学习率的方式稍有差异,但主要思想都是基于历史的累计梯度去计算一个当前较优的学习率。 -   -**(1)incremental GD/stochastic GD** -   -在 GD 中,是需要遍历所有的点之后才计算 $w$ 的变化的;但是,在 stochastic GD 中,每输入一个点,就根据该点计算下一步的 $w$,这样,不仅可以从 batch training 变成 online training 方法,而且每次是按照单点的最优方向而不是整体的最优方向前进,从而相当于在朝目标前进的路上多拐了好多弯,有可能逃出局部最优。 +## 13.6 常见的损失函数有哪些? -   -**(2)momentum 方法** -   -momentum 相当与记忆住上一次的更新。在每次的更新中,都要加一个 $k$ 倍的上一次更新 量。这样,也不再是按照标准路线前进,每次的步骤都容易受到上一次的影响,从而可能会逃 出局部最优。另外,也会加大步长,从而加快收敛。 +机器学习通过对算法中的目标函数进行不断求解优化,得到最终想要的结果。分类和回归问题中,通常使用损失函数或代价函数作为目标函数。 -## 13.11 常见的损失函数? +损失函数用来评价预测值和真实值不一样的程度。通常损失函数越好,模型的性能也越好。 -   -机器学习通过对算法中的目标函数进行不断求解优化,得到最终想要的结果。分类和回归 问题中,通常使用损失函数或代价函数作为目标函数。 -   -损失函数用来评价预测值和真实值不一样的程度。通常损失函数越好,模型的性能也越好。 -   -损失函数可分为经验风险损失函数和结构风险损失函数。经验风险损失函数指预测结果和 实际结果的差别,结构风险损失函数是在经验风险损失函数上加上正则项。 +损失函数可分为**经验风险损失**和**结构风险损失**。经验风险损失是根据已知数据得到的损失。结构风险损失是为了防止模型被过度拟合已知数据而加入的惩罚项。 -   下面介绍常用的损失函数: - +**(1)0-1 损失函数**    -**1)$0-1$ 损失函数** -   -如果预测值和目标值相等,值为 $0$,如果不相等,值为 $1$: +如果预测值和目标值相等,值为 0,如果不相等,值为 1: $$ L(Y,f(x))= \left\{ @@ -243,15 +123,15 @@ L(Y,f(x))= $$    -**2)绝对值损失函数** +**(2)绝对值损失函数**    -和 $0-1$ 损失函数相似,绝对值损失函数表示为: +和 0-1 损失函数相似,绝对值损失函数表示为: $$ L(Y,f(x))=|Y-f(x)|. $$    -**3)平方损失函数** +**(3)平方损失函数** $$ L(Y|f(x))=\sum_{N}(Y-f(x))^2. $$ @@ -260,16 +140,16 @@ $$ 这点可从最小二乘法和欧几里得距离角度理解。最小二乘法的原理是,最优拟合曲线应该 使所有点到回归直线的距离和最小。    -**4)$log$ 对数损失函数** +**(4)log 对数损失函数** $$ L(Y,P(Y|X))=-logP(Y|X). $$    -常见的逻辑回归使用的就是对数损失函数,有很多人认为逻辑回归的损失函数式平方损失, 其实不然。逻辑回归它假设样本服从伯努利分布,进而求得满足该分布的似然函数,接着取对 数求极值等。逻辑回归推导出的经验风险函数是最小化负的似然函数,从损失函数的角度看, 就是 $log$ 损失函数。 +常见的逻辑回归使用的就是对数损失函数,有很多人认为逻辑回归的损失函数式平方损失, 其实不然。逻辑回归它假设样本服从伯努利分布,进而求得满足该分布的似然函数,接着取对 数求极值等。逻辑回归推导出的经验风险函数是最小化负的似然函数,从损失函数的角度看, 就是 log 损失函数。    -**5)指数损失函数** +**(5)指数损失函数**    指数损失函数的标准形式为: $$ @@ -280,7 +160,7 @@ $$ 例如 AdaBoost 就是以指数损失函数为损失函数。    -**6)Hinge 损失函数** +**(6)Hinge 损失函数**    Hinge 损失函数的标准形式如下: $$ @@ -288,7 +168,7 @@ L(y)=max(0, 1-ty). $$    -其中 $y$ 是预测值,范围为$(-1,1)$, $t$ 为目标值,其为$-1$ 或 $1$。 +其中 y 是预测值,范围为(-1,1), t 为目标值,其为-1 或 1。    在线性支持向量机中,最优化问题可等价于: $$ @@ -303,289 +183,158 @@ $$    其中$l(wx_i+by_i))$是Hinge损失函数,$\lVert w^2 \rVert$可看做为正则化项。 -## 13.14 如何进行特征选择(feature selection)? - -### 13.14.1 如何考虑特征选择 - -   -当数据预处理完成后,我们需要选择有意义的特征输入机器学习的算法和模型进行训练。通常来说,从两个方面考虑来选择特征: - -   -(1)特征是否发散:如果一个特征不发散,例如方差接近于 $0$,也就是说样本在这个特 征上基本上没有差异,这个特征对于样本的区分并没有什么用。 -   -(2)特征与目标的相关性:这点比较显见,与目标相关性高的特征,应当优选选择。除移除低方差法外,本文介绍的其他方法均从相关性考虑。 - -### 13.14.2 特征选择方法分类 - -   -根据特征选择的形式又可以将特征选择方法分为 $3$ 种: - -   -(1)Filter:过滤法,按照发散性或者相关性对各个特征进行评分,设定阈值或者待选择 -阈值的个数,选择特征。 -   -(2)Wrapper:包装法,根据目标函数(通常是预测效果评分),每次选择若干特征,或 -者排除若干特征。 -   -(3)Embedded:嵌入法,先使用某些机器学习的算法和模型进行训练,得到各个特征的权值系数,根据系数从大到小选择特征。类似于 Filter 方法,但是是通过训练来确定特征的优劣。 - -### 13.14.3 特征选择目的 +## 13.7 如何进行特征选择(feature selection)? -   -(1)减少特征数量、降维,使模型泛化能力更强,减少过拟合; -   -(2)增强对特征和特征值之间的理解。拿到数据集,一个特征选择方法,往往很难同时完成这两个目的。通常情况下,选择一种自己最熟悉或者最方便的特征选择方法(往往目的是降维,而忽略了对特征和数据理解的目的)。 本文将结合 Scikit-learn 提供的例子介绍几种常用的特征选择方法,它们各自的优缺点和问题。 +### 13.7.1 特征类型有哪些? -## 13.15 梯度消失/梯度爆炸原因,以及解决方法 +对象本身会有许多属性。所谓特征,即能在某方面最能表征对象的一个或者一组属性。一般地,我们可以把特征分为如下三个类型: -### 13.15.1 为什么要使用梯度更新规则? +(1)相关特征:对于特定的任务和场景具有一定帮助的属性,这些属性通常能有效提升算法性能; -   -在介绍梯度消失以及爆炸之前,先简单说一说梯度消失的根源—–深度神经网络和反向传 播。目前深度学习方法中,深度神经网络的发展造就了我们可以构建更深层的网络完成更复杂 的任务,深层网络比如深度卷积网络,LSTM 等等,而且最终结果表明,在处理复杂任务上, 深度网络比浅层的网络具有更好的效果。但是,目前优化神经网络的方法都是基于反向传播的 思想,即根据损失函数计算的误差通过梯度反向传播的方式,指导深度网络权值的更新优化。 这样做是有一定原因的,首先,深层网络由许多非线性层堆叠而来,每一层非线性层都可以视 为是一个非线性函数 $f(x)$($f(x)$非线性来自于非线性激活函数),因此整个深度网络可以视为是一个复合的非线性多元函数: -$$F(x)=f_n(\cdots f_3(f_2(f_1(x)*\theta_1+b)*\theta_2+b)\cdots)$$ +(2)无关特征:在特定的任务和场景下完全无用的属性,这些属性对对象在本目标环境下完全无用; -   -我们最终的目的是希望这个多元函数可以很好的完成输入到输出之间的映射,假设不同的输入,输出的最优解是$g(x)$ ,那么,优化深度网络就是为了寻找到合适的权值,满足 $Loss=L(g(x),F(x))$取得极小值点,比如最简单的损失函数: -$$ -Loss = \lVert g(x)-f(x) \rVert^2_2. -$$ +(3)冗余特征:同样是在特定的任务和场景下具有一定帮助的属性,但这类属性已过多的存在,不具有产生任何新的信息的能力。 -   -假设损失函数的数据空间是下图这样的,我们最优的权值就是为了寻找下图中的最小值点, 对于这种数学寻找最小值问题,采用梯度下降的方法再适合不过了。 -![](./img/ch13/figure_13_15_1.png) -
图 13.15.1
+### 13.7.2 如何考虑特征选择 -### 13.15.2 梯度消失、爆炸原因? +当完成数据预处理之后,对特定的场景和目标而言很多维度上的特征都是不具有任何判别或者表征能力的,所以需要对数据在维度上进行筛选。一般地,可以从以下两个方面考虑来选择特征: -   -梯度消失与梯度爆炸其实是一种情况,看接下来的文章就知道了。两种情况下梯度消失经 常出现,一是在深层网络中,二是采用了不合适的损失函数,比如 sigmoid。梯度爆炸一般出 现在深层网络和权值初始化值太大的情况下,下面分别从这两个角度分析梯度消失和爆炸的原因。 +(1)特征是否具有发散性:某个特征若在所有样本上的都是一样的或者接近一致,即方差非常小。 也就是说所有样本的都具有一致的表现,那这些就不具有任何信息。 -   -(1)深层网络角度 -   -对激活函数进行求导,如果此部分大于 $1$,那么层数增多的时候,最终的求出的梯度更新 将以指数形式增加,即发生**梯度爆炸**,如果此部分小于 $1$,那么随着层数增多,求出的梯度更 新信息将会以指数形式衰减,即发生了**梯度消失**。 -   -从深层网络角度来讲,不同的层学习的速度差异很大,表现为网络中靠近输出的层学习的 情况很好,靠近输入的层学习的很慢,有时甚至训练了很久,前几层的权值和刚开始随机初始 化的值差不多。因此,梯度消失、爆炸,其根本原因在于反向传播训练法则,属于先天不足, 另外多说一句,Hinton 提出 capsule 的原因就是为了彻底抛弃反向传播,如果真能大范围普及, 那真是一个革命。 +(2)特征与目标的相关性:与目标相关性高的特征,应当优选选择。 -   -(2)激活函数角度 -   -计算权值更新信息的时候需要计算前层偏导信息,因此如果激活函数选择不合适,比如使用 sigmoid,梯度消失就会很明显了,原因看下图,左图是sigmoid的损失函数图,右边是其倒数的图像,如果使用 sigmoid 作为损失函数,其梯度是不可能超过 $0.25$ 的,这样经过链式求导之后,很容易发生梯度消失。 -![](./img/ch13/figure_13_15_2.png) -
图 13.15.2 sigmod函数与其导数
+### 13.7.3 特征选择方法分类 -### 13.15.3 梯度消失、爆炸的解决方案 +根据特征选择的形式又可以将特征选择方法分为 3 种: +(1)过滤法:按照发散性或者相关性对各个特征进行评分,设定阈值或者待选择阈值的个数,选择特征。 -   -**方案1-预训练加微调** -   -此方法来自Hinton在2006年发表的一篇论文,Hinton为了解决梯度的问题,提出采取无监督逐层训练方法,其基本思想是每次训练一层隐节点,训练时将上一层隐节点的输出作为输入,而本层隐节点的输出作为下一层隐节点的输入,此过程就是逐层“预训练”(pre-training);在预训练完成后,再对整个网络进行“微调”(fine-tunning)。Hinton在训练深度信念网络(Deep Belief Networks中,使用了这个方法,在各层预训练完成后,再利用BP算法对整个网络进行训练。此思想相当于是先寻找局部最优,然后整合起来寻找全局最优,此方法有一定的好处,但是目前应用的不是很多了。 +(2)包装法:根据目标函数(通常是预测效果评分),每次选择若干特征,或者排除若干特征。 -   -**方案2-梯度剪切、正则** -   -梯度剪切这个方案主要是针对梯度爆炸提出的,其思想是设置一个梯度剪切阈值,然后更新梯度的时候,如果梯度超过这个阈值,那么就将其强制限制在这个范围之内。这可以防止梯度爆炸。 -   -另外一种解决梯度爆炸的手段是采用权重正则化(weithts regularization)比较常见的是l1l1正则,和l2l2正则,在各个深度框架中都有相应的API可以使用正则化。 +(3)嵌入法:先使用某些机器学习的算法和模型进行训练,得到各个特征的权值系数,根据系数从大到小选择特征。 -   -**方案3-relu、leakrelu、elu等激活函数** -   -**Relu** -   -思想也很简单,如果激活函数的导数为1,那么就不存在梯度消失爆炸的问题了,每层的网络都可以得到相同的更新速度,relu就这样应运而生。 -   -relu函数的导数在正数部分是恒等于1的,因此在深层网络中使用relu激活函数就不会导致梯度消失和爆炸的问题。 -relu的主要贡献在于: -   -(1)解决了梯度消失、爆炸的问题 -   -(2)计算方便,计算速度快 -   -(3)加速了网络的训练 +### 13.7.4 特征选择目的 -   -同时也存在一些缺点: -   -(1)由于负数部分恒为0,会导致一些神经元无法激活(可通过设置小学习率部分解决); -   -(2)输出不是以0为中心的。 +(1)减少特征维度,使模型泛化能力更强,减少过拟合; -   -**leakrelu**  -   -leakrelu就是为了解决relu的0区间带来的影响,其数学表达为:leakrelu$=max(k*x,0)$其中$k$是leak系数,一般选择$0.01$或者$0.02$,或者通过学习而来。 +(2)降低任务目标的学习难度; -   -**方案4-batchnorm** -   -Batchnorm是深度学习发展以来提出的最重要的成果之一了,目前已经被广泛的应用到了各大网络中,具有加速网络收敛速度,提升训练稳定性的效果,Batchnorm本质上是解决反向传播过程中的梯度问题。Batchnorm全名是Batch Normalization,简称BN,即批规范化,通过规范化操作将输出信号$x$规范化到均值为$0$,方差为$1$保证网络的稳定性。 +(3)一组优秀的特征通常能有效的降低模型复杂度,提升模型效率 -   -**方案5-残差结构**   -   -事实上,就是残差网络的出现导致了Imagenet比赛的终结,自从残差提出后,几乎所有的深度网络都离不开残差的身影,相比较之前的几层,几十层的深度网络,在残差网络面前都不值一提,残差可以很轻松的构建几百层,一千多层的网络而不用担心梯度消失过快的问题,原因就在于残差的捷径(shortcut)部分。 - -   -**方案6-LSTM** -   -LSTM全称是长短期记忆网络(long-short term memory networks),是不那么容易发生梯度消失的,主要原因在于LSTM内部复杂的“门”(gates)。 - -## 13.16 深度学习为什么不用二阶优化 - -1. 二阶优化方法可以用到深度学习网络中,比如DistBelief,《Large-scale L-BFGS using MapReduce》.采用了数据并行的方法解决了海量数据下L-BFGS算法的可用性问题。 -2. 二阶优化方法目前还不适用于深度学习训练中,主要存在问题是: -(1)最重要的问题是二阶方法的计算量大,训练较慢。 -(2)求导不易,实现比SGD这类一阶方法复杂。 -(3)另外其优点在深度学习中无法展现出来,主要是二阶方法能够更快地求得更高精度的解,这在浅层模型是有益的,但是在神经网络这类深层模型中对参数的精度要求不高,相反 相对而言不高的精度对模型还有益处,能够提高模型的泛化能力。 -(4)稳定性。题主要明白的一点事,越简单的东西往往越robust,对于优化算法也是这样。梯度下降等一阶算法只要步长不选太大基本都不会出问题,但二阶方法遍地是坑,数值稳定性啊等等。 +## 13.8 梯度消失/梯度爆炸原因,以及解决方法 -## 13.17 怎样优化你的深度学习系统? +### 13.8.1 为什么要使用梯度更新规则? -   -你可能有很多想法去改善你的系统,比如,你可能想我们去收集更多的训练数据吧。或者你会说,可能你的训练集的多样性还不够,你应该收集更多不同姿势的猫咪图片,或者更多样化的反例集。或者你想再用梯度下降训练算法,训练久一点。或者你想尝试用一个完全不同的优化算法,比如Adam优化算法。或者尝试使用规模更大或者更小的神经网络。或者你想试试dropout或者正则化。或者你想修改网络的架构,比如修改激活函数,改变隐藏单元的数目之类的方法。 - -   -当你尝试优化一个深度学习系统时,你通常可以有很多想法可以去试,问题在于,如果你做出了错误的选择,你完全有可能白费6个月的时间,往错误的方向前进,在6个月之后才意识到这方法根本不管用。比如,我见过一些团队花了6个月时间收集更多数据,却在6个月之后发现,这些数据几乎没有改善他们系统的性能。所以,假设你的项目没有6个月的时间可以浪费,如果有快速有效的方法能够判断哪些想法是靠谱的,或者甚至提出新的想法,判断哪些是值得一试的想法,哪些是可以放心舍弃的。 +目前深度学习的火热,其最大的功臣之一就是反向传播。反向传播,即根据损失评价函数计算的误差,计算得到梯度,通过梯度反向传播的方式,指导深度网络权值的更新优化。这样做的原因在于,深层网络由许多非线性层堆叠而来,每一层非线性层都可以视为是一个非线性函数,因此整个深度网络可以视为是一个复合的非线性多元函数: +$$ +F(x)=f_n(\cdots f_3(f_2(f_1(x)*\theta_1+b)*\theta_2+b)\cdots) +$$ +我们最终的目的是希望这个多元函数可以很好的完成输入到输出之间的映射,假设不同的输入,输出的最优解是g(x) ,那么,优化深度网络就是为了寻找到合适的权值,满足 Loss=L(g(x),F(x))取得极小值点,比如最简单的损失函数: +$$ +Loss = \lVert g(x)-f(x) \rVert^2_2. -   -我希望在这门课程中,可以教给你们一些策略,一些分析机器学习问题的方法,可以指引你们朝着最有希望的方向前进。这门课中,我会和你们分享我在搭建和部署大量深度学习产品时学到的经验和教训,我想这些内容是这门课程独有的。比如说,很多大学深度学习课程很少提到这些策略。事实上,机器学习策略在深度学习的时代也在变化,因为现在对于深度学习算法来说能够做到的事情,比上一代机器学习算法大不一样。我希望这些策略能帮助你们提高效率,让你们的深度学习系统更快投入实用。 +假设损失函数的数据空间是下图这样的,我们最优的权值就是为了寻找下图中的最小值点, 对于这种数学寻找最小值问题,采用梯度下降的方法再适合不过了。 +![](./img/ch13/figure_13_15_1.png) +$$ -## 13.18 为什么要设置单一数字评估指标? +假设损失函数的数据空间是下图这样的,我们最优的权值就是为了寻找下图中的最小值点, 对于这种数学寻找最小值问题,采用梯度下降的方法再适合不过了。 -   -无论你是调整超参数,或者是尝试不同的学习算法,或者在搭建机器学习系统时尝试不同手段,你会发现,如果你有一个单实数评估指标,你的进展会快得多,它可以快速告诉你,新尝试的手段比之前的手段好还是差。所以当团队开始进行机器学习项目时,我经常推荐他们为问题设置一个单实数评估指标。 +![](./img/ch13/figure_13_15_1.png) -   -我发现很多机器学习团队就是这样,有一个定义明确的开发集用来测量查准率和查全率,再加上这样一个单一数值评估指标,有时我叫单实数评估指标,能让你快速判断分类器或者分类器更好。所以有这样一个开发集,加上单实数评估指标,你的迭代速度肯定会很快,它可以加速改进您的机器学习算法的迭代过程。 -![](./img/ch13/figure_13_18_1.png)
图 13.8.1
-## 13.19 满足和优化指标(Satisficing and optimizing metrics) +### 13.8.2 梯度消失/爆炸产生的原因? -   -要把你顾及到的所有事情组合成单实数评估指标有时并不容易,在那些情况里,我发现有时候设立满足和优化指标是很重要的,让我告诉你是什么意思吧。 -![](./img/ch13/figure_13_19_1.png) -
图 13.9.1
+本质上,梯度消失和爆炸是一种情况。在深层网络中,由于网络过深,如果初始得到的梯度过小,或者传播途中在某一层上过小,则在之后的层上得到的梯度会越来越小,即产生了梯度消失。梯度爆炸也是同样的。一般地,不合理的初始化以及激活函数,如sigmoid等,都会导致梯度过大或者过小,从而引起消失/爆炸。 -   -假设你已经决定你很看重猫分类器的分类准确度,这可以是分数或者用其他衡量准确度的指标。但除了准确度之外,我们还需要考虑运行时间,就是需要多长时间来分类一张图。分类器需要$80$毫秒,需要$95$毫秒,C需要$1500$毫秒,就是说需要$1.5$秒来分类图像。 +下面分别从网络深度角度以及激活函数角度进行解释: +(1)网络深度 -   -你可以这么做,将准确度和运行时间组合成一个整体评估指标。所以成本,比如说,总体成本是,这种组合方式可能太刻意,只用这样的公式来组合准确度和运行时间,两个数值的线性加权求和。 +若在网络很深时,若权重初始化较小,各层上的相乘得到的数值都会0-1之间的小数,而激活函数梯度也是0-1之间的数。那么连乘后,结果数值就会变得非常小,导致**梯度消失**。若权重初始化较大,大到乘以激活函数的导数都大于1,那么连乘后,可能会导致求导的结果很大,形成**梯度爆炸**。 -   -你还可以做其他事情,就是你可能选择一个分类器,能够最大限度提高准确度,但必须满足运行时间要求,就是对图像进行分类所需的时间必须小于等于$100$毫秒。所以在这种情况下,我们就说准确度是一个优化指标,因为你想要准确度最大化,你想做的尽可能准确,但是运行时间就是我们所说的满足指标,意思是它必须足够好,它只需要小于$100$毫秒,达到之后,你不在乎这指标有多好,或者至少你不会那么在乎。所以这是一个相当合理的权衡方式,或者说 将准确度和运行时间结合起来的方式。实际情况可能是,只要运行时间少于 100 毫秒,你的用 户就不会在乎运行时间是 100 毫秒还是 50 毫秒,甚至更快。 +(2)激活函数 +如果激活函数选择不合适,比如使用 sigmoid,梯度消失就会很明显了,原因看下图,左图是sigmoid的损失函数图,右边是其倒数的图像,如果使用 sigmoid 作为损失函数,其梯度是不可能超过 0.25 的,这样经过链式求导之后,很容易发生梯度消失。 +![](./img/ch13/figure_13_15_2.png) -   -通过定义优化和满足指标,就可以给你提供一个明确的方式,去选择“最好的”分类器。在 这种情况下分类器 B 最好,因为在所有的运行时间都小于 100 毫秒的分类器中,它的准确度最好。 +
图 13.8.2 sigmod函数与其导数
-   -总结一下,如果你需要顾及多个指标,比如说,有一个优化指标,你想尽可能优化的,然 后还有一个或多个满足指标,需要满足的,需要达到一定的门槛。现在你就有一个全自动的方 法,在观察多个成本大小时,选出"最好的"那个。现在这些评估指标必须是在训练集或开发集 或测试集上计算或求出来的。所以你还需要做一件事,就是设立训练集、开发集,还有测试集。 在下一个视频里,我想和大家分享一些如何设置训练、开发和测试集的指导方针,我们下一个 视频继续。 +### 13.8.3 梯度消失、爆炸的解决方案 -## 13.20 怎样划分训练/开发/测试集 +**1、预训练加微调** +此方法来自Hinton在2006年发表的一篇论文,Hinton为了解决梯度的问题,提出采取无监督逐层训练方法,其基本思想是每次训练一层隐节点,训练时将上一层隐节点的输出作为输入,而本层隐节点的输出作为下一层隐节点的输入,此过程就是逐层“预训练”(pre-training);在预训练完成后,再对整个网络进行“微调”(fine-tunning)。Hinton在训练深度信念网络(Deep Belief Networks中,使用了这个方法,在各层预训练完成后,再利用BP算法对整个网络进行训练。此思想相当于是先寻找局部最优,然后整合起来寻找全局最优,此方法有一定的好处,但是目前应用的不是很多了。 -   -设立训练集,开发集和测试集的方式大大影响了你或者你的团队在建立机器学习应用方面取得进展的速度。同样的团队,即使是大公司里的团队,在设立这些数据集的方式,真的会让团队的进展变慢而不是加快,我们看看应该如何设立这些数据集,让你的团队效率最大化。 +**2、梯度剪切、正则** +梯度剪切这个方案主要是针对梯度爆炸提出的,其思想是设置一个梯度剪切阈值,然后更新梯度的时候,如果梯度超过这个阈值,那么就将其强制限制在这个范围之内。这可以防止梯度爆炸。 +另外一种解决梯度爆炸的手段是采用权重正则化(weithts regularization)比较常见的是L1和L2正则。 -   -我建议你们不要这样,而是让你的开发集和测试集来自同一分布。我的意思是这样,你们要记住,我想就是设立你的开发集加上一个单实数评估指标,这就是像是定下目标,然后告诉你的团队,那就是你要瞄准的靶心,因为你一旦建立了这样的开发集和指标,团队就可以快速迭代,尝试不同的想法,跑实验,可以很快地使用开发集和指标去评估不同分类器,然后尝试选出最好的那个。所以,机器学习团队一般都很擅长使用不同方法去逼近目标,然后不断迭代,不断逼近靶心。所以,针对开发集上的指标优化。 +**3、ReLu、leakReLu等激活函数** +(1)ReLu:其函数的导数在正数部分是恒等于1,这样在深层网络中,在激活函数部分就不存在导致梯度过大或者过小的问题,缓解了梯度消失或者爆炸。同时也方便计算。当然,其也存在存在一些缺点,例如过滤到了负数部分,导致部分信息的丢失,输出的数据分布不在以0为中心,改变了数据分布。 +(2)leakrelu:就是为了解决relu的0区间带来的影响,其数学表达为:leakrelu=max(k*x,0)其中k是leak系数,一般选择0.01或者0.02,或者通过学习而来。 -   -所以我建议你们在设立开发集和测试集时,要选择这样的开发集和测试集,能够反映你未来会得到的数据,认为很重要的数据,必须得到好结果的数据,特别是,这里的开发集和测试集可能来自同一个分布。所以不管你未来会得到什么样的数据,一旦你的算法效果不错,要尝试收集类似的数据,而且,不管那些数据是什么,都要随机分配到开发集和测试集上。因为这样,你才能将瞄准想要的目标,让你的团队高效迭代来逼近同一个目标,希望最好是同一个目标。 +**4、batchnorm** +Batchnorm是深度学习发展以来提出的最重要的成果之一了,目前已经被广泛的应用到了各大网络中,具有加速网络收敛速度,提升训练稳定性的效果,Batchnorm本质上是解决反向传播过程中的梯度问题。Batchnorm全名是Batch Normalization,简称BN,即批规范化,通过规范化操作将输出信号x规范化到均值为0,方差为1保证网络的稳定性。 -   -我们还没提到如何设立训练集,我们会在之后的视频里谈谈如何设立训练集,但这个视频的重点在于,设立开发集以及评估指标,真的就定义了你要瞄准的目标。我们希望通过在同一分布中设立开发集和测试集,你就可以瞄准你所希望的机器学习团队瞄准的目标。而设立训练集的方式则会影响你逼近那个目标有多快,但我们可以在另一个讲座里提到。我知道有一些机器学习团队,他们如果能遵循这个方针,就可以省下几个月的工作,所以我希望这些方针也能帮到你们。 +**5、残差结构** +残差的方式,能使得深层的网络梯度通过跳级连接路径直接返回到浅层部分,使得网络无论多深都能将梯度进行有效的回传。 -   -接下来,实际上你的开发集和测试集的规模,如何选择它们的大小,在深度学习时代也在变化,我们会在下一个视频里提到这些内容。 +**6、LSTM** +LSTM全称是长短期记忆网络(long-short term memory networks),是不那么容易发生梯度消失的,主要原因在于LSTM内部复杂的“门”(gates)。在计算时,将过程中的梯度进行了抵消。 -## 13.21 如何划分开发/测试集大小 +## 13.9 深度学习为什么不用二阶优化? -   -你可能听说过一条经验法则,在机器学习中,把你取得的全部数据用$70/30$比例分成训练集和测试集。或者如果你必须设立训练集、开发集和测试集,你会这么分$60\%$训练集,$20\%$开发集,$20\%$测试集。在机器学习的早期,这样分是相当合理的,特别是以前的数据集大小要小得多。所以如果你总共有100个样本,这样$70/30$或者$60/20/20$分的经验法则是相当合理的。如果你有几千个样本或者有一万个样本,这些做法也还是合理的。 +目前深度学习中,反向传播主要是依靠一阶梯度。二阶梯度在理论和实际上都是可以应用都网络中的,但相比于一阶梯度,二阶优化会存在以下一些主要问题: +(1)计算量大,训练非常慢。 +(2)二阶方法能够更快地求得更高精度的解,这在浅层模型是有益的。而在神经网络这类深层模型中对参数的精度要求不高,甚至不高的精度对模型还有益处,能够提高模型的泛化能力。 +(3)稳定性。二阶方法能更快求高精度的解,同样对数据本身要的精度也会相应的变高,这就会导致稳定性上的问题。 -   -但在现代机器学习中,我们更习惯操作规模大得多的数据集,比如说你有$1$百万个训练样本,这样分可能更合理,$98\%$作为训练集,$1\%$开发集,$1\%$测试集,我们用和缩写来表示开发集和测试集。因为如果你有$1$百万个样本,那么$1\%$就是$10,000$个样本,这对于开发集和测试集来说可能已经够了。所以在现代深度学习时代,有时我们拥有大得多的数据集,所以使用小于$20\%$的比例或者小于$30\%$比例的数据作为开发集和测试集也是合理的。而且因为深度学习算法对数据的胃口很大,我们可以看到那些有海量数据集的问题,有更高比例的数据划分到训练集里,那么测试集呢? +## 13.10 为什么要设置单一数字评估指标,设置指标的意义? -   -总结一下,在大数据时代旧的经验规则,这个$70/30$不再适用了。现在流行的是把大量数据分到训练集,然后少量数据分到开发集和测试集,特别是当你有一个非常大的数据集时。以前的经验法则其实是为了确保开发集足够大,能够达到它的目的,就是帮你评估不同的想法,然后选出还是更好。测试集的目的是评估你最终的成本偏差,你只需要设立足够大的测试集,可以用来这么评估就行了,可能只需要远远小于总体数据量的$30\%$。 +在训练模型时,无论是调整超参数,还是调整不同的模型算法,我们都需要有一个评价指标,这个评价标准能帮助我们很快的了解,新的尝试后模型的性能是否更优。例如在分类时,我们通常会选择选择准确率,当样本不平衡时,查准率和查全率又会是更好的评价指标。所以在训练模型时,如果设置了单一数字的评估指标通常能很快的反应出我们模型的改进是否直接产生了收益,从而加速我们的算法改进过程。若在训练过程中,发现优化目标进一步深入,现有指标无法完全反应进一步的目标时,就需要重新选择评估指标了。 -   -所以我希望本视频能给你们一点指导和建议,让你们知道如何在深度学习时代设立开发和测试集。接下来,有时候在研究机器学习的问题途中,你可能需要更改评估指标,或者改动你的开发集和测试集,我们会讲什么时候需要这样做。 +## 13.11训练/验证/测试集的定义及划分 -## 13.22 什么时候该改变开发/测试集和指标? +训练、验证、测试集在机器学习领域是非常重要的三个内容。三者共同组成了整个项目的性能的上限和走向。 -   -我们来看一个例子,假设你在构建一个猫分类器,试图找到很多猫的照片,向你的爱猫人士用户展示,你决定使用的指标是分类错误率。所以算法和分别有3%错误率和5%错误率,所以算法似乎做得更好。 +训练集:用于模型训练的样本集合,样本占用量是最大的; -   -但我们实际试一下这些算法,你观察一下这些算法,算法由于某些原因,把很多色情图像分类成猫了。如果你部署算法,那么用户就会看到更多猫图,因为它识别猫的错误率只有$3\%$,但它同时也会给用户推送一些色情图像,这是你的公司完全不能接受的,你的用户也完全不能接受。相比之下,算法有$5\%$的错误率,这样分类器就得到较少的图像,但它不会推送色情图像。所以从你们公司的角度来看,以及从用户接受的角度来看,算法实际上是一个更好的算法,因为它不让任何色情图像通过。 +验证集:用于训练过程中的模型性能评价,跟着性能评价才能更好的调参; -   -那么在这个例子中,发生的事情就是,算法A在评估指标上做得更好,它的错误率达到$3\%$,但实际上是个更糟糕的算法。在这种情况下,评估指标加上开发集它们都倾向于选择算法,因为它们会说,看算法A的错误率较低,这是你们自己定下来的指标评估出来的。但你和你的用户更倾向于使用算法,因为它不会将色情图像分类为猫。所以当这种情况发生时,当你的评估指标无法正确衡量算法之间的优劣排序时,在这种情况下,原来的指标错误地预测算法A是更好的算法这就发出了信号,你应该改变评估指标了,或者要改变开发集或测试集。在这种情况下,你用的分类错误率指标可以写成这样: +测试集:用于最终模型的一次最终评价,直接反应了模型的性能。 -   -但粗略的结论是,如果你的评估指标无法正确评估好算法的排名,那么就需要花时间定义一个新的评估指标。这是定义评估指标的其中一种可能方式(上述加权法)。评估指标的意义在于,准确告诉你已知两个分类器,哪一个更适合你的应用。就这个视频的内容而言,我们不需要太注重新错误率指标是怎么定义的,关键在于,如果你对旧的错误率指标不满意,那就不要一直沿用你不满意的错误率指标,而应该尝试定义一个新的指标,能够更加符合你的偏好,定义出实际更适合的算法。 +在划分上,可以分两种情况: -   -所以方针是,如果你在指标上表现很好,在当前开发集或者开发集和测试集分布中表现很好,但你的实际应用程序,你真正关注的地方表现不好,那么就需要修改指标或者你的开发测试集。换句话说,如果你发现你的开发测试集都是这些高质量图像,但在开发测试集上做的评估无法预测你的应用实际的表现。因为你的应用处理的是低质量图像,那么就应该改变你的开发测试集,让你的数据更能反映你实际需要处理好的数据。 +1、在样本量有限的情况下,有时候会把验证集和测试集合并。实际中,若划分为三类,那么训练集:验证集:测试集=6:2:2;若是两类,则训练集:验证集=7:3。这里需要主要在数据量不够多的情况,验证集和测试集需要占的数据比例比较多,以充分了解模型的泛化性。 -   -但总体方针就是,如果你当前的指标和当前用来评估的数据和你真正关心必须做好的事情关系不大,那就应该更改你的指标或者你的开发测试集,让它们能更够好地反映你的算法需要处理好的数据。 +2、在海量样本的情况下,这种情况在目前深度学习中会比较常见。此时由于数据量巨大,我们不需要将过多的数据用于验证和测试集。例如拥有1百万样本时,我们按训练集:验证集:测试集=98:1:1的比例划分,1%的验证和1%的测试集都已经拥有了1万个样本。这已足够验证模型性能了。 -## 13.23 设置评估指标的意义? +此外,三个数据集的划分不是一次就可以的,若调试过程中发现,三者得到的性能评价差异很大时,可以重新划分以确定是数据集划分的问题导致还是由模型本身导致的。其次,若评价指标发生变化,而导致模型性能差异在三者上很大时,同样可重新划分确认排除数据问题,以方便进一步的优化。 -   -评估指标的意义在于,准确告诉你已知两个分类器,哪一个更适合你的应用。就这个视频的内容而言,我们不需要太注重新错误率指标是怎么定义的,关键在于,如果你对旧的错误率指标不满意,那就不要一直沿用你不满意的错误率指标,而应该尝试定义一个新的指标,能够更加符合你的偏好,定义出实际更适合的算法。 - -## 13.24 什么是可避免偏差? - -   -[http://www.ai-start.com/dl2017/lesson3-week1.html](http://www.ai-start.com/dl2017/lesson3-week1.html -) +## 13.12 什么是可避免偏差? -   所以要给这些概念命名一下,这不是广泛使用的术语,但我觉得这么说思考起来比较流畅。就是把这个差值,贝叶斯错误率或者对贝叶斯错误率的估计和训练错误率之间的差值称为可避免偏差,你可能希望一直提高训练集表现,直到你接近贝叶斯错误率,但实际上你也不希望做到比贝叶斯错误率更好,这理论上是不可能超过贝叶斯错误率的,除非过拟合。而这个训练错误率和开发错误率之前的差值,就大概说明你的算法在方差问题上还有多少改善空间。 +可避免偏差这个词说明了有一些别的偏差,或者错误率有个无法超越的最低水平,那就是说如果贝叶斯错误率是7.5%。你实际上并不想得到低于该级别的错误率,所以你不会说你的训练错误率是8%,然后8%就衡量了例子中的偏差大小。你应该说,可避免偏差可能在0.5%左右,或者0.5%是可避免偏差的指标。而这个2%是方差的指标,所以要减少这个2%比减少这个0.5%空间要大得多。而在左边的例子中,这7%衡量了可避免偏差大小,而2\%衡量了方差大小。所以在左边这个例子里,专注减少可避免偏差可能潜力更大。 -   -可避免偏差这个词说明了有一些别的偏差,或者错误率有个无法超越的最低水平,那就是说如果贝叶斯错误率是$7.5\%$。你实际上并不想得到低于该级别的错误率,所以你不会说你的训练错误率是$8\%$,然后$8\%$就衡量了例子中的偏差大小。你应该说,可避免偏差可能在$0.5\%$左右,或者$0.5\%$是可避免偏差的指标。而这个$2\%$是方差的指标,所以要减少这个$2\%$比减少这个$0.5\%$空间要大得多。而在左边的例子中,这$7\%$衡量了可避免偏差大小,而$2\%$衡量了方差大小。所以在左边这个例子里,专注减少可避免偏差可能潜力更大。 +## 13.13 什么是TOP5错误率? -## 13.25 什么是TOP5错误率? +通常对于分类系统而言,系统会对某个未知样本进行所有已知样本的匹配,并给出该未知样本在每个已知类别上的概率。其中最大的概率就是系统系统判定最可能的一个类别。TOP5则就是在前五个最大概率的类别。TOP5错误率,即预测最可能的五类都不是该样本类别的错误率。 -   -top1就是你预测的label取最后概率向量里面最大的那一个作为预测结果,你的预测结果中概率最大的那个类必须是正确类别才算预测正确。而top5就是最后概率向量最大的前五名中出现了正确概率即为预测正确。 - -   -ImageNet 项目是一个用于物体对象识别检索大型视觉数据库。截止$2016$年,ImageNet 已经对超过一千万个图像的url进行手动注释,标记图像的类别。在至少一百万张图像中还提供了边界框。自$2010$年以来,ImageNet 举办一年一度的软件竞赛,叫做 ImageNet 大尺度视觉识别挑战(ImageNet Large Scale Visual Recognition Challenge,ILSVRC)。主要内容是通过算法程序实现正确分类和探测识别物体与场景,评价标准就是Top-5 错误率。 - -   -Top-5 错误率 -   -ILSRVRC(ImageNet 图像分类大赛) 比赛设置如下:$1000$类图像分类问题,训练数据集$126$万张图像,验证集$5$万张,测试集$10$万张(标注未公布)。评价标准采用 top-5 错误率——即对一张图像预测$5$个类别,只要有一个和人工标注类别相同就算对,否则算错。 +TOP5错误率通常会用于在类别数量很多或者细粒度类别的模型系统。典型地,例如著名的ImageNet ,其包含了1000个类别。通常就会采用TOP5错误率。 -## 13.26 什么是人类水平错误率? +## 13.14 什么是人类水平错误率? -   -人类水平错误率的定义,就是如果你想要替代或估计贝叶斯错误率,那么一队经验丰富的医生讨论和辩论之后,可以达到$0.5\%$的错误率。我们知道贝叶斯错误率小于等于$0.5\%$,因为有些系统,这些医生团队可以达到$0.5\%$的错误率。所以根据定义,最优错误率必须在$0.5\%$以下。我们不知道多少更好,也许有一个更大的团队,更有经验的医生能做得更好,所以也许比$0.5\%$好一点。但是我们知道最优错误率不能高于$0.5\%$,那么在这个背景下,我就可以用$0.5\%$估计贝叶斯错误率。所以我将人类水平定义为$0.5\%$,至少如果你希望使用人类水平错误来分析偏差和方差的时候,就像上个视频那样。 - -   +人类水平错误率的定义,就是如果你想要替代或估计贝叶斯错误率,那么一队经验丰富的医生讨论和辩论之后,可以达到0.5%的错误率。我们知道贝叶斯错误率小于等于0.5%,因为有些系统,这些医生团队可以达到0.5%的错误率。所以根据定义,最优错误率必须在0.5%以下。我们不知道多少更好,也许有一个更大的团队,更有经验的医生能做得更好,所以也许比0.5%好一点。但是我们知道最优错误率不能高于0.\%,那么在这个背景下,我就可以用0.5%估计贝叶斯错误率。 现在,为了发表研究论文或者部署系统,也许人类水平错误率的定义可以不一样,你可以使用1%,只要你超越了一个普通医生的表现,如果能达到这种水平,那系统已经达到实用了。也许超过一名放射科医生,一名医生的表现,意味着系统在一些情况下可以有部署价值了。 -## 13.27 可避免偏差、几大错误率之间的关系? +## 13.15 可避免偏差、几大错误率之间的关系? -   -要了解为什么这个很重要,我们来看一个错误率分析的例子。比方说,在医学图像诊断例子中,你的训练错误率是$5\%$,你的开发错误率是$6\%$。而在上一张幻灯片的例子中,我们的人类水平表现,我将它看成是贝叶斯错误率的替代品,取决于你是否将它定义成普通单个医生的表现,还是有经验的医生或医生团队的表现,你可能会用$1\%$或$0.7\%$或$0.5\%$。同时也回想一下,前面视频中的定义,贝叶斯错误率或者说贝叶斯错误率的估计和训练错误率直接的差值就衡量了所谓的可避免偏差,这(训练误差与开发误差之间的差值)可以衡量或者估计你的学习算法的方差问题有多严重。 - -   -所以在这个第一个例子中,无论你做出哪些选择,可避免偏差大概是$4\%$,这个值我想介于……,如果你取$1\%$就是$4\%$,如果你取$0.5\%$就是$4.5\%$,而这个差距(训练误差与开发误差之间的差值)是$1\%$。所以在这个例子中,我得说,不管你怎么定义人类水平错误率,使用单个普通医生的错误率定义,还是单个经验丰富医生的错误率定义或经验丰富的医生团队的错误率定义,这是$4\%$还是$4.5\%$,这明显比都比方差问题更大。所以在这种情况下,你应该专注于减少偏差的技术,例如培训更大的网络。 +要了解为什么这个很重要,我们来看一个错误率分析的例子。比方说,在医学图像诊断例子中,你的训练错误率是5%,你的开发错误率是6%。而在上一张幻灯片的例子中,我们的人类水平表现,我将它看成是贝叶斯错误率的替代品,取决于你是否将它定义成普通单个医生的表现,还是有经验的医生或医生团队的表现,你可能会用1%或0.7%或0.5%。同时也回想一下,前面视频中的定义,贝叶斯错误率或者说贝叶斯错误率的估计和训练错误率直接的差值就衡量了所谓的可避免偏差,这(训练误差与开发误差之间的差值)可以衡量或者估计你的学习算法的方差问题有多严重。 +所以在这个第一个例子中,无论你做出哪些选择,可避免偏差大概是4\%,如果你取1%就是4%,如果你取0.5%就是4.5%,而这个差距(训练误差与开发误差之间的差值)是1%。所以在这个例子中,我得说,不管你怎么定义人类水平错误率,使用单个普通医生的错误率定义,还是单个经验丰富医生的错误率定义或经验丰富的医生团队的错误率定义,这是4%还是4.5%,这明显比都比方差问题更大。所以在这种情况下,你应该专注于减少偏差的技术,例如培训更大的网络。 -## 13.28 怎样选取可避免偏差及贝叶斯错误率? +## 13.16 怎样选取可避免偏差及贝叶斯错误率?    就是比如你的训练错误率是0.7%,所以你现在已经做得很好了,你的开发错误率是$0.8\%$。在这种情况下,你用$0.5\%$来估计贝叶斯错误率关系就很大。因为在这种情况下,你测量到的可避免偏差是$0.2\%$,这是你测量到的方差问题$0.1\%$的两倍,这表明也许偏差和方差都存在问题。但是,可避免偏差问题更严重。在这个例子中,我们在上一张幻灯片中讨论的是$0.5\%$,就是对贝叶斯错误率的最佳估计,因为一群人类医生可以实现这一目标。如果你用$0.7$代替贝叶斯错误率,你测得的可避免偏差基本上是$0\%$,那你就可能忽略可避免偏差了。实际上你应该试试能不能在训练集上做得更好。 -## 13.29 怎样减少方差? +## 13.17 怎样减少方差?    如果你的算法方差较高,可以尝试下面的技巧: @@ -601,12 +350,12 @@ ILSRVRC(ImageNet 图像分类大赛) 比赛设置如下:$1000$类图像分    (5)缩小模型(例如减少网络层数和神经元数量):谨慎使用。这种技巧可以减少方差,同时也可能增加偏差。然而,我并不推荐使用这种技巧来解决方差问题。添加正则化通常会获得更好的分类性能。缩小模型的优点在于减少计算成本,以更快的速度来训练模型。如果模型的训练速度非常重要,那么就想尽一切方法来缩小模型。但是如果目标是减少方差,不是那么在意计算成本,可以考虑添加正则化。 -## 13.30 贝叶斯错误率的最佳估计 +## 13.18 贝叶斯错误率的最佳估计    对于这样的问题,更好的估计贝叶斯错误率很有必要,可以帮助你更好地估计可避免偏差和方差,这样你就能更好的做出决策,选择减少偏差的策略,还是减少方差的策略。 -## 13.31 举机器学习超过单个人类表现几个例子? +## 13.19 举机器学习超过单个人类表现几个例子?    现在,机器学习有很多问题已经可以大大超越人类水平了。例如,我想网络广告,估计某个用户点击广告的可能性,可能学习算法做到的水平已经超越任何人类了。还有提出产品建议,向你推荐电影或书籍之类的任务。我想今天的网站做到的水平已经超越你最亲近的朋友了。还有物流预测,从到开车需要多久,或者预测快递车从开到需要多少时间。或者预测某人会不会偿还贷款,这样你就能判断是否批准这人的贷款。我想这些问题都是今天的机器学习远远超过了单个人类的表现。 @@ -614,7 +363,7 @@ ILSRVRC(ImageNet 图像分类大赛) 比赛设置如下:$1000$类图像分    除了这些问题,今天已经有语音识别系统超越人类水平了,还有一些计算机视觉任务,一些图像识别任务,计算机已经超越了人类水平。但是由于人类对这种自然感知任务非常擅长,我想计算机达到那种水平要难得多。还有一些医疗方面的任务,比如阅读ECG或诊断皮肤癌,或者某些特定领域的放射科读图任务,这些任务计算机做得非常好了,也许超越了单个人类的水平。 -## 13.32如何改善你的模型? +## 13.20如何改善你的模型?    你们学过正交化,如何设立开发集和测试集,用人类水平错误率来估计贝叶斯错误率以及如何估计可避免偏差和方差。我们现在把它们全部组合起来写成一套指导方针,如何提高学习算法性能的指导方针。 @@ -637,7 +386,7 @@ ILSRVRC(ImageNet 图像分类大赛) 比赛设置如下:$1000$类图像分 在之后的课程里我们会详细介绍的,新的神经网络架构能否更好地拟合你的训练集,有时也很难预先判断,但有时换架构可能会得到好得多的结果。 -## 13.33 理解误差分析 +## 13.21 理解误差分析    如果你希望让学习算法能够胜任人类能做的任务,但你的学习算法还没有达到人类的表现,那么人工检查一下你的算法犯的错误也许可以让你了解接下来应该做什么。这个过程称为错误分析,我们从一个例子开始讲吧。 @@ -651,7 +400,7 @@ ILSRVRC(ImageNet 图像分类大赛) 比赛设置如下:$1000$类图像分    所以总结一下,进行错误分析,你应该找一组错误样本,可能在你的开发集里或者测试集里,观察错误标记的样本,看看假阳性(false positives)和假阴性(false negatives),统计属于不同错误类型的错误数量。在这个过程中,你可能会得到启发,归纳出新的错误类型,就像我们看到的那样。如果你过了一遍错误样本,然后说,天,有这么多Instagram滤镜或Snapchat滤镜,这些滤镜干扰了我的分类器,你就可以在途中新建一个错误类型。总之,通过统计不同错误标记类型占总数的百分比,可以帮你发现哪些问题需要优先解决,或者给你构思新优化方向的灵感。在做错误分析的时候,有时你会注意到开发集里有些样本被错误标记了,这时应该怎么做呢?我们下一个视频来讨论。 -## 13.34 为什么值得花时间查看错误标记数据? +## 13.22 为什么值得花时间查看错误标记数据?    最后我讲几个建议: @@ -660,7 +409,7 @@ ILSRVRC(ImageNet 图像分类大赛) 比赛设置如下:$1000$类图像分    其次,不知道为什么,我看一些工程师和研究人员不愿意亲自去看这些样本,也许做这些事情很无聊,坐下来看100或几百个样本来统计错误数量,但我经常亲自这么做。当我带领一个机器学习团队时,我想知道它所犯的错误,我会亲自去看看这些数据,尝试和一部分错误作斗争。我想就因为花了这几分钟,或者几个小时去亲自统计数据,真的可以帮你找到需要优先处理的任务,我发现花时间亲自检查数据非常值得,所以我强烈建议你们这样做,如果你在搭建你的机器学习系统的话,然后你想确定应该优先尝试哪些想法,或者哪些方向。 -## 13.35 快速搭建初始系统的意义? +## 13.23 快速搭建初始系统的意义?    一般来说,对于几乎所有的机器学习程序可能会有$50$个不同的方向可以前进,并且每个方向都是相对合理的可以改善你的系统。但挑战在于,你如何选择一个方向集中精力处理。即使我已经在语音识别领域工作多年了,如果我要为一个新应用程序域构建新系统,我还是觉得很难不花时间去思考这个问题就直接选择方向。所以我建议你们,如果你想搭建全新的机器学习程序,就是快速搭好你的第一个系统,然后开始迭代。我的意思是我建议你快速设立开发集和测试集还有指标,这样就决定了你的目标所在,如果你的目标定错了,之后改也是可以的。但一定要设立某个目标,然后我建议你马上搭好一个机器学习系统原型,然后找到训练集,训练一下,看看效果,开始理解你的算法表现如何,在开发集测试集,你的评估指标上表现如何。当你建立第一个系统后,你就可以马上用到之前说的偏差方差分析,还有之前最后几个视频讨论的错误分析,来确定下一步优先做什么。特别是如果错误分析让你了解到大部分的错误的来源是说话人远离麦克风,这对语音识别构成特殊挑战,那么你就有很好的理由去集中精力研究这些技术,所谓远场语音识别的技术,这基本上就是处理说话人离麦克风很远的情况。 @@ -668,7 +417,7 @@ ILSRVRC(ImageNet 图像分类大赛) 比赛设置如下:$1000$类图像分    建立这个初始系统的所有意义在于,它可以是一个快速和粗糙的实现(quick and dirty implementation),你知道的,别想太多。初始系统的全部意义在于,有一个学习过的系统,有一个训练过的系统,让你确定偏差方差的范围,就可以知道下一步应该优先做什么,让你能够进行错误分析,可以观察一些错误,然后想出所有能走的方向,哪些是实际上最有希望的方向。 -## 13.36 为什么要在不同的划分上训练及测试? +## 13.24 为什么要在不同的划分上训练及测试?    深度学习算法对训练数据的胃口很大,当你收集到足够多带标签的数据构成训练集时,算法效果最好,这导致很多团队用尽一切办法收集数据,然后把它们堆到训练集里,让训练的数据量更大,即使有些数据,甚至是大部分数据都来自和开发集、测试集不同的分布。在深度学习时代,越来越多的团队都用来自和开发集、测试集分布不同的数据来训练,这里有一些微妙的地方,一些最佳做法来处理训练集和测试集存在差异的情况,我们来看看。 @@ -684,7 +433,7 @@ ILSRVRC(ImageNet 图像分类大赛) 比赛设置如下:$1000$类图像分    我建议你走另外一条路,就是这样,训练集,比如说还是$205,000$张图片,我们的训练集是来自网页下载的$200,000$张图片,然后如果需要的话,再加上$5000$张来自手机上传的图片。然后对于开发集和测试集,这数据集的大小是按比例画的,你的开发集和测试集都是手机图。而训练集包含了来自网页的$20$万张图片,还有$5000$张来自应用的图片,开发集就是$2500$张来自应用的图片,测试集也是$2500$张来自应用的图片。这样将数据分成训练集、开发集和测试集的好处在于,现在你瞄准的目标就是你想要处理的目标,你告诉你的团队,我的开发集包含的数据全部来自手机上传,这是你真正关心的图片分布。我们试试搭建一个学习系统,让系统在处理手机上传图片分布时效果良好。缺点在于,当然了,现在你的训练集分布和你的开发集、测试集分布并不一样。但事实证明,这样把数据分成训练、开发和测试集,在长期能给你带来更好的系统性能。我们以后会讨论一些特殊的技巧,可以处理 训练集的分布和开发集和测试集分布不一样的情况。 -## 13.37 如何解决数据不匹配问题? +## 13.25 如何解决数据不匹配问题?    如果您的训练集来自和开发测试集不同的分布,如果错误分析显示你有一个数据不匹配的问题该怎么办?这个问题没有完全系统的解决方案,但我们可以看看一些可以尝试的事情。如果我发现有严重的数据不匹配问题,我通常会亲自做错误分析,尝试了解训练集和开发测试集的具体差异。技术上,为了避免对测试集过拟合,要做错误分析,你应该人工去看开发集而不是测试集。 @@ -713,7 +462,7 @@ ILSRVRC(ImageNet 图像分类大赛) 比赛设置如下:$1000$类图像分    所以这就是如何处理数据不匹配问题,接下来,我想和你分享一些想法就是如何从多种类型的数据同时学习。 -## 13.38 梯度检验注意事项? +## 13.26 梯度检验注意事项?    首先,不要在训练中使用梯度检验,它只用于调试。我的意思是,计算所有值的是一个非常漫长的计算过程,为了实施梯度下降,你必须使用和 backprop来计算,并使用backprop来计算导数,只要调试的时候,你才会计算它,来确认数值是否接近。完成后,你会关闭梯度检验,梯度检验的每一个迭代过程都不执行它,因为它太慢了。 @@ -733,7 +482,7 @@ ILSRVRC(ImageNet 图像分类大赛) 比赛设置如下:$1000$类图像分    这就是梯度检验,恭喜大家,这是本周最后一课了。回顾这一周,我们讲了如何配置训练集,验证集和测试集,如何分析偏差和方差,如何处理高偏差或高方差以及高偏差和高方差并存的问题,如何在神经网络中应用不同形式的正则化,如正则化和dropout,还有加快神经网络训练速度的技巧,最后是梯度检验。这一周我们学习了很多内容,你可以在本周编程作业中多多练习这些概念。祝你好运,期待下周再见。 -## 13.39什么是随机梯度下降? +## 13.27什么是随机梯度下降?    随机梯度下降,简称SGD,是指梯度下降算法在训练集上,对每一个训练数据都计算误差并更新模型。 @@ -752,7 +501,7 @@ ILSRVRC(ImageNet 图像分类大赛) 比赛设置如下:$1000$类图像分 * 频繁的更新产生的噪声可能导致模型参数和模型误差来回跳动(更大的方差)。 * 这种伴有噪声的更新方式也能让算法难以稳定的收敛于一点。 -## 13.40什么是批量梯度下降? +## 13.28什么是批量梯度下降?    批量梯度下降对训练集上每一个数据都计算误差,但只在所有训练数据计算完成后才更新模型。 @@ -772,7 +521,7 @@ ILSRVRC(ImageNet 图像分类大赛) 比赛设置如下:$1000$类图像分 * 通常来说,批量梯度下降算法需要把所有的训练数据都存放在内存中。 * 在大数据集上,训练速度会非常慢。 -## 13.41什么是小批量梯度下降? +## 13.29什么是小批量梯度下降?    小批量梯度下降把训练集划分为很多批,对每一批(batch)计算误差并更新参数。 @@ -792,7 +541,7 @@ ILSRVRC(ImageNet 图像分类大赛) 比赛设置如下:$1000$类图像分 * 小批量梯度下降给算法增加了一个超参数batch size。 * 和批量梯度下降一样,每一个batch上的误差需要累加。 -## 13.42怎么配置mini-batch梯度下降 +## 13.30怎么配置mini-batch梯度下降    Mini-batch梯度下降对于深度学习大部分应用是最常用的方法。 @@ -822,7 +571,7 @@ batch size通常从1到几百之间选择,比如$32$是一个很好的默认    batch size和学习率几乎不受其他超参数的影响,因此可以放到最后再优化。batch size确定之后,可以被视为固定值,从而去优化其他超参数(如果使用了动量超参数则例外)。 -## 13.43 局部最优的问题 +## 13.31 局部最优的问题    在深度学习研究早期,人们总是担心优化算法会困在极差的局部最优,不过随着深度学习理论不断发展,我们对局部最优的理解也发生了改变。我向你展示一下现在我们怎么看待局部最优以及深度学习中的优化问题。 @@ -880,7 +629,7 @@ batch size和学习率几乎不受其他超参数的影响,因此可以放到    因为你的网络要解决优化问题,说实话,要面临如此之高的维度空间,我觉得没有人有那么好的直觉,知道这些空间长什么样,而且我们对它们的理解还在不断发展,不过我希望这一点能够让你更好地理解优化算法所面临的问题。 -## 13.44 提升算法性能思路 +## 13.32 提升算法性能思路    这个列表里提到的思路并完全,但是一个好的开始。  diff --git "a/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_18_1.png" "b/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_18_1.png" deleted file mode 100644 index 8edafaf4..00000000 Binary files "a/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_18_1.png" and /dev/null differ diff --git "a/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_19_1.png" "b/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_19_1.png" deleted file mode 100644 index 4c283d61..00000000 Binary files "a/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/img/ch13/figure_13_19_1.png" and /dev/null differ diff --git "a/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/readme.md" "b/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/readme.md" deleted file mode 100644 index 4ebe256b..00000000 --- "a/ch13_\344\274\230\345\214\226\347\256\227\346\263\225/readme.md" +++ /dev/null @@ -1,14 +0,0 @@ -########################################################### - -### 深度学习500问-第 * 章 xxx - -**负责人(排名不分先后):** -xxx研究生-xxx(xxx) -xxx博士生-xxx -xxx-xxx - - -**贡献者(排名不分先后):** -内容贡献者可自加信息 - -########################################################### \ No newline at end of file diff --git "a/ch14_\350\266\205\345\217\202\346\225\260\350\260\203\346\225\264/img/ch14/14.14.png" "b/ch14_\350\266\205\345\217\202\346\225\260\350\260\203\346\225\264/img/ch14/14.14.png" index cfc05bfe..5f0dd49c 100644 Binary files "a/ch14_\350\266\205\345\217\202\346\225\260\350\260\203\346\225\264/img/ch14/14.14.png" and "b/ch14_\350\266\205\345\217\202\346\225\260\350\260\203\346\225\264/img/ch14/14.14.png" differ diff --git "a/ch14_\350\266\205\345\217\202\346\225\260\350\260\203\346\225\264/img/ch14/NASNet\347\232\204RNN\346\216\247\345\210\266\345\231\250.png" "b/ch14_\350\266\205\345\217\202\346\225\260\350\260\203\346\225\264/img/ch14/NASNet\347\232\204RNN\346\216\247\345\210\266\345\231\250.png" new file mode 100644 index 00000000..d1f8f8b7 Binary files /dev/null and "b/ch14_\350\266\205\345\217\202\346\225\260\350\260\203\346\225\264/img/ch14/NASNet\347\232\204RNN\346\216\247\345\210\266\345\231\250.png" differ diff --git "a/ch14_\350\266\205\345\217\202\346\225\260\350\260\203\346\225\264/img/ch14/NAS\346\220\234\347\264\242\347\255\226\347\225\245.png" "b/ch14_\350\266\205\345\217\202\346\225\260\350\260\203\346\225\264/img/ch14/NAS\346\220\234\347\264\242\347\255\226\347\225\245.png" new file mode 100644 index 00000000..40f7cc23 Binary files /dev/null and "b/ch14_\350\266\205\345\217\202\346\225\260\350\260\203\346\225\264/img/ch14/NAS\346\220\234\347\264\242\347\255\226\347\225\245.png" differ diff --git "a/ch14_\350\266\205\345\217\202\346\225\260\350\260\203\346\225\264/img/ch14/RNN\346\216\247\345\210\266\345\231\250.png" "b/ch14_\350\266\205\345\217\202\346\225\260\350\260\203\346\225\264/img/ch14/RNN\346\216\247\345\210\266\345\231\250.png" new file mode 100644 index 00000000..958b60e0 Binary files /dev/null and "b/ch14_\350\266\205\345\217\202\346\225\260\350\260\203\346\225\264/img/ch14/RNN\346\216\247\345\210\266\345\231\250.png" differ diff --git "a/ch14_\350\266\205\345\217\202\346\225\260\350\260\203\346\225\264/img/ch14/\345\257\274\346\225\260.png" "b/ch14_\350\266\205\345\217\202\346\225\260\350\260\203\346\225\264/img/ch14/\345\257\274\346\225\260.png" deleted file mode 100644 index 4eb7ca20..00000000 Binary files "a/ch14_\350\266\205\345\217\202\346\225\260\350\260\203\346\225\264/img/ch14/\345\257\274\346\225\260.png" and /dev/null differ diff --git "a/ch14_\350\266\205\345\217\202\346\225\260\350\260\203\346\225\264/img/ch14/\346\200\235\347\273\264\345\257\274\345\233\276.png" "b/ch14_\350\266\205\345\217\202\346\225\260\350\260\203\346\225\264/img/ch14/\346\200\235\347\273\264\345\257\274\345\233\276.png" new file mode 100644 index 00000000..8ec2bfc3 Binary files /dev/null and "b/ch14_\350\266\205\345\217\202\346\225\260\350\260\203\346\225\264/img/ch14/\346\200\235\347\273\264\345\257\274\345\233\276.png" differ diff --git "a/ch14_\350\266\205\345\217\202\346\225\260\350\260\203\346\225\264/modify_log.txt" "b/ch14_\350\266\205\345\217\202\346\225\260\350\260\203\346\225\264/modify_log.txt" index 110a1976..ea1c0553 100644 --- "a/ch14_\350\266\205\345\217\202\346\225\260\350\260\203\346\225\264/modify_log.txt" +++ "b/ch14_\350\266\205\345\217\202\346\225\260\350\260\203\346\225\264/modify_log.txt" @@ -34,6 +34,11 @@ 14.20 什么是神经网络架构搜索(NAS) 14.21 如何调试模型? -<----shw2018-2018-11-15----> +<----shw2018-2018-11-26----> 修改整体结构:modify by 王超锋 +增加思维导图 +<----shw2018-2018-12-9----> +修改整体结构:modify by 王超锋 +修改思维导图 +调整结构,修改部分答案描述 \ No newline at end of file diff --git "a/ch14_\350\266\205\345\217\202\346\225\260\350\260\203\346\225\264/\347\254\254\345\215\201\345\233\233\347\253\240_\350\266\205\345\217\202\346\225\260\350\260\203\346\225\264.md" "b/ch14_\350\266\205\345\217\202\346\225\260\350\260\203\346\225\264/\347\254\254\345\215\201\345\233\233\347\253\240_\350\266\205\345\217\202\346\225\260\350\260\203\346\225\264.md" index 726308e0..be8d1ed3 100644 --- "a/ch14_\350\266\205\345\217\202\346\225\260\350\260\203\346\225\264/\347\254\254\345\215\201\345\233\233\347\253\240_\350\266\205\345\217\202\346\225\260\350\260\203\346\225\264.md" +++ "b/ch14_\350\266\205\345\217\202\346\225\260\350\260\203\346\225\264/\347\254\254\345\215\201\345\233\233\347\253\240_\350\266\205\345\217\202\346\225\260\350\260\203\346\225\264.md" @@ -11,17 +11,21 @@ > Updater: [sjsdfg](https://github.com/sjsdfg),王超锋 ## 14.1 写在前面 -  关于训练深度学习模型最难的事情之一是你要处理的参数的数量。无论是从网络本身的层宽(宽度)、层数(深度)、连接方式,还是损失函数的超参数设计和调试,亦或者是学习率、批样本数量、优化器参数等等。这些大量的参数都会有网络模型最终的有效容限直接或者间接的影响。面对如此众多的参数,如果我们要一一对其优化调整,所需的无论是时间、资源都是不切实际。结果证实一些超参数比其它的更为重要,因此认识各个超参数的作用和其可能会造成的影响是深度学习训练中必不可少的一项重要技能。 +​ 关于训练深度学习模型最难的事情之一是你要处理的参数的数量。无论是从网络本身的层宽(宽度)、层数(深度)、连接方式,还是损失函数的超参数设计和调试,亦或者是学习率、批样本数量、优化器参数等等。这些大量的参数都会有网络模型最终的有效容限直接或者间接的影响。面对如此众多的参数,如果我们要一一对其优化调整,所需的无论是时间、资源都是不切实际。结果证实一些超参数比其它的更为重要,因此认识各个超参数的作用和其可能会造成的影响是深度学习训练中必不可少的一项重要技能。 -​ 目前,超参数调整一般分为手动调整和自动优化超参数两种。本章节不会过多阐述所有超参数的详细原理,如果需要了解这部分,您可以翻阅前面的基础章节或者查阅相关文献资料。当然,下面会讲到的一些超参数优化的建议是根据笔者们的实践以及部分文献资料得到认知建议,并不是非常严格且一定有效的,很多研究者可能会很不同意某些的观点或有着不同的直觉,这都是可保留讨论的,因为这很依赖于数据本身情况。 +​ 超参数调整可以说是深度学习中理论和实际联系最重要的一个环节。目前,深度学习仍存在很多不可解释的部分,如何设计优化出好的网络可以为深度学习理论的探索提供重要的支持。超参数调整一般分为手动调整和自动优化超参数两种。读者可先浏览思维导图,本章节不会过多阐述所有超参数的详细原理,如果需要了解这部分,您可以翻阅前面的基础章节或者查阅相关文献资料。当然,下面会讲到的一些超参数优化的建议是根据笔者们的实践以及部分文献资料得到认知建议,并不是非常严格且一定有效的,很多研究者可能会很不同意某些的观点或有着不同的直觉,这都是可保留讨论的,因为这很依赖于数据本身情况。 -## 14.2 超参数概述 +![](.\img\ch14\思维导图.png) -### 14.2.1 什么是超参数,参数和超参数的区别 +​ + +## 14.2 超参数概念 + +### 14.2.1 什么是超参数,参数和超参数的区别? ​ 区分两者最大的一点就是是否通过数据来进行调整,模型参数通常是有数据来驱动调整,超参数则不需要数据来驱动,而是在训练前或者训练中人为的进行调整的参数。例如卷积核的具体核参数就是指模型参数,这是有数据驱动的。而学习率则是人为来进行调整的超参数。这里需要注意的是,通常情况下卷积核数量、卷积核尺寸这些也是超参数,注意与卷积核的核参数区分。 -### 14.2.2 神经网络中包含哪些超参数 +### 14.2.2 神经网络中包含哪些超参数?    通常可以将超参数分为三类:网络参数、优化参数、正则化参数。 ​ 网络参数:可指网络层与层之间的交互方式(相加、相乘或者串接等)、卷积核数量和卷积核尺寸、网络层数(也称深度)和激活函数等。 @@ -30,9 +34,9 @@ ​ 正则化:权重衰减系数,丢弃法比率(dropout) -### 14.2.3 模型优化寻找最优解和正则项之间的关系 +### 14.2.3 为什么要进行超参数调优? -​ 网络模型优化调整的目的是为了寻找到全局最优解(或者相比更好的局部最优解),而正则项又希望模型尽量拟合到最优。两者通常情况下,存在一定的对立,但两者的目标是一致的,即最小化期望风险。模型优化希望最小化经验风险,而容易陷入过拟合,正则项用来约束模型复杂度。所以如何平衡两者之间的关系,得到最优或者较优的解就是超参数调整优化的目的。 +​ 本质上,这是模型优化寻找最优解和正则项之间的关系。网络模型优化调整的目的是为了寻找到全局最优解(或者相比更好的局部最优解),而正则项又希望模型尽量拟合到最优。两者通常情况下,存在一定的对立,但两者的目标是一致的,即最小化期望风险。模型优化希望最小化经验风险,而容易陷入过拟合,正则项用来约束模型复杂度。所以如何平衡两者之间的关系,得到最优或者较优的解就是超参数调整优化的目的。 ### 14.2.4 超参数的重要性顺序 @@ -43,7 +47,7 @@ - 最后,**Adam优化器的超参数、权重衰减系数、丢弃法比率(dropout)和网络参数**。在这里说明下,这些参数重要性放在最后**并不等价于这些参数不重要**。而是表示这些参数在大部分实践中**不建议过多尝试**,例如Adam优化器中的*β1,β2,ϵ*,常设为 0.9、0.999、10−8就会有不错的表现。权重衰减系数通常会有个建议值,例如0.0005 ,使用建议值即可,不必过多尝试。dropout通常会在全连接层之间使用防止过拟合,建议比率控制在[0.2,0.5]之间。使用dropout时需要特别注意两点:一、在RNN中,如果直接放在memory cell中,循环会放大噪声,扰乱学习。一般会建议放在输入和输出层;二、不建议dropout后直接跟上batchnorm,dropout很可能影响batchnorm计算统计量,导致方差偏移,这种情况下会使得推理阶段出现模型完全垮掉的极端情况;网络参数通常也属于超参数的范围内,通常情况下增加网络层数能增加模型的容限能力,但模型真正有效的容限能力还和样本数量和质量、层之间的关系等有关,所以一般情况下会选择先固定网络层数,调优到一定阶段或者有大量的硬件资源支持可以在网络深度上进行进一步调整。 -### 14.2.5 部分超参数如何影响模型性能 +### 14.2.5 部分超参数如何影响模型性能? | 超参数 | 如何影响模型容量 | 原因 | 注意事项 | | :----------------: | :------------------------------: | :----------------------------------------------------------: | :----------------------------------------------------------: | @@ -62,7 +66,7 @@ | :----------------: | :----------------------------------------------------------: | :----------------------------------------------------------: | | 初始学习率 | SGD: [1e-2, 1e-1]
momentum: [1e-3, 1e-2]
Adagrad: [1e-3, 1e-2]
Adadelta: [1e-2, 1e-1]
RMSprop: [1e-3, 1e-2]
Adam: [1e-3, 1e-2]
Adamax: [1e-3, 1e-2]
Nadam: [1e-3, 1e-2] | 这些范围通常是指从头开始训练的情况。若是微调,初始学习率可在降低一到两个数量级。 | | 损失函数部分超参数 | 多个损失函数之间,损失值之间尽量相近,不建议超过或者低于两个数量级 | 这是指多个损失组合的情况,不一定完全正确。单个损失超参数需结合实际情况。 | -| 批样本数量 | [1:1024] | 当批样本数量过大(大于6000)或者等于1时,需要注意学习策略或者BN的替代品。 | +| 批样本数量 | [1:1024] | 当批样本数量过大(大于6000)或者等于1时,需要注意学习策略或者内部归一化方式的调整。 | | 丢弃法比率 | [0, 0.5] | | | 权重衰减系数 | [0, 1e-4] | | | 卷积核尺寸 | [7x7],[5x5],[3x3],[1x1], [7x1,1x7] | | @@ -80,8 +84,9 @@ 3、监控训练和验证误差。首先很多情况下,我们忽略代码的规范性和算法撰写正确性验证,这点上容易产生致命的影响。在训练和验证都存在问题时,首先请确认自己的代码是否正确。其次,根据训练和验证误差进一步追踪模型的拟合状态。若训练数据集很小,此时监控误差则显得格外重要。确定了模型的拟合状态对进一步调整学习率的策略的选择或者其他有效超参数的选择则会更得心应手。 4、反向传播数值的计算,这种情况通常适合自己设计一个新操作的情况。目前大部分流行框架都已包含自动求导部分,但并不一定是完全符合你的要求的。验证求导是否正确的方式是比较自动求导的结果和有限差分计算结果是否一致。所谓有限差分即导数的定义,使用一个极小的值近似导数。 - -![](./img/ch14/%E5%AF%BC%E6%95%B0.png) +$$ +f^{'}(x_0) = \lim_{n\rightarrow0}\frac{\Delta y}{\Delta x} = \lim_{n\rightarrow0}\frac{f(x_0+\Delta x -f(x_0))}{\Delta x} +$$ ### 14.3.2 为什么要做学习率调整? @@ -89,7 +94,7 @@ ### 14.3.3 学习率调整策略有哪些? -通常情况下,大部分学习率调整策略都是衰减学习率,当然也有部分增大学习率的策略。这里结合TensorFlow的内置方法来举例。 +通常情况下,大部分学习率调整策略都是衰减学习率,但有时若增大学习率也同样起到奇效。这里结合TensorFlow的内置方法来举例。 1、**exponential_decay**和**natural_exp_decay** @@ -123,15 +128,19 @@ polynomial_decay(learning_rate, global_step, decay_steps, 多项式衰减,计算如下: -global_step = min(global_step,decay_steps) +$$ +global setp = min(global step, decay steps) +$$ -decayed_learning_rate = (learning_rate-end_learning_rate)*(1-global_step/decay_steps)^ (power)+end_learning_rate +$$ +lr_{decayed} = (lr-lr_{end})*(1-{globalstep\over decaysteps})^{power} +lr_{end} +$$ -有别去上述两种,多项式衰减则是在每一步迭代上都会调整学习率。主要看Power参数,若Power为1,则是下图中的红色直线;若power小于1,则是开1/power次方,为蓝色线;绿色线为指数,power大于1。 +有别于上述两种,多项式衰减则是在每一步迭代上都会调整学习率。主要看Power参数,若Power为1,则是下图中的红色直线;若power小于1,则是开1/power次方,为蓝色线;绿色线为指数,power大于1。 ![](.\img\ch14\多项式衰减.jpeg) -此外,需要注意的是参数cycle,cycle对应的是一种周期循环调整的方式,主要的目的在后期防止在一个局部极小值震荡,若跳出该区域或许能得到更有的结果。这里说明cycle的方式不止可以在多项式中应用,可配合类似的周期函数进行衰减,如下图。 +此外,需要注意的是参数cycle,cycle对应的是一种周期循环调整的方式。这种cycle策略主要目的在后期防止在一个局部极小值震荡,若跳出该区域或许能得到更有的结果。这里说明cycle的方式不止可以在多项式中应用,可配合类似的周期函数进行衰减,如下图。 ![](.\img\ch14\cycle衰减.jpeg) @@ -162,7 +171,7 @@ cosine_decay_restarts(learning_rate, global_step, first_decay_steps, t_mul=2.0, m_mul=1.0, alpha=0.0, name=None) ``` -余弦重启衰减,即余弦版本的cycle策略,作用与多项式衰减中的cycle相同。区别在于余弦重启衰减会重新回到初始学习率,拉长周期,而多项式版本则会逐周期衰减。 +余弦衰减,即余弦版本的cycle策略,作用与多项式衰减中的cycle相同。区别在于余弦重启衰减会重新回到初始学习率,拉长周期,而多项式版本则会逐周期衰减。 ![](.\img\ch14\余弦cycle衰减.jpeg) @@ -186,28 +195,11 @@ linear_cosine_decay(learning_rate, global_step, decay_steps, ### 14.3.4 极端批样本数量下,如何训练网络? +​ 极端批样本情况一般是指batch size为1或者batch size在6000以上的情况。这两种情况,在使用不合理的情况下都会导致模型最终性能无法达到最优甚至是崩溃的情况。 +​ 在目标检测、分割或者3D图像等输入图像尺寸较大的场景,通常batch size 会非常小。而在14.2.4中,我们已经讲到这种情况会导致梯度的不稳定以及batchnorm统计的不准确。针对梯度不稳定的问题,通常不会太致命,若训练中发现梯度不稳定导致性能的严重降低时可采用累计梯度的策略,即每次计算完不反向更新,而是累计多次的误差后进行一次更新,这是一种在内存有限情况下实现有效梯度更新的一个策略。batch size过小通常对batchnorm的影响是最大的,若网络模型中存在batchnorm,batch size若只为1或者2时会对训练结果产生非常大的影响。这时通常有两种策略,一、若模型使用了预训练网络,可冻结预训练网络中batchnorm的模型参数,有效降低batch size引起的统计量变化的影响。二、在网络不是过深或者过于复杂时可直接移除batchnorm或者使用groupnorm代替batchnorm,前者不多阐释,后者是有FAIR提出的一种用于减少batch对batchnorm影响,其主要策略是先将特征在通道上进行分组,然后在组内进行归一化。即归一化操作上完全与batch size无关。这种groupnorm的策略被证实在极小批量网络训练上能达到较优秀的性能。当然这里也引入里group这个超参数,一般情况下建议不宜取group为1或者各通道单独为组的group数量,可结合实际网络稍加调试。 -### 14.3.5 为什么卷积核设计尺寸都是奇数 - -主要原因有两点: - -- 保证像素点中心位置,避免位置信息偏移 -- 填充边缘时能保证两边都能填充,原矩阵依然对称 - -### 14.3.6 权重共享的形式有哪些,为什么要权重共享 - -权重共享的形式: - -- 深度学习中,权重共享最具代表性的就是卷积网络的卷积操作。卷积相比于全连接神经网络参数大大减少; -- 多任务网络中,通常为了降低每个任务的计算量,会共享一个骨干网络。 -- 一些相同尺度下的结构化递归网络 - -权重共享的好处: - -​ 权重共享一定程度上能增强参数之间的联系,获得更好的共性特征。同时很大程度上降低了网络的参数,节省计算量和计算所需内存(当然,结构化递归并不节省计算量)。此外权重共享能起到很好正则的作用。正则化的目的是为了降低模型复杂度,防止过拟合,而权重共享则正好降低了模型的参数和复杂度。 - -​ 因此一个设计优秀的权重共享方式,在降低计算量的同时,通常会较独享网络有更好的效果。 +​ 为了降低训练时间的成本,多机多卡的分布式系统通常会使用超大的batch size进行网络训练。同样的在14.2.4中,我们提到了超大batch size会带来梯度方向过于一致而导致的精度大幅度降低的问题。这时通常可采用层自适应速率缩放(LARS)算法。从理论认知上将,batch size增大会减少反向传播的梯度更新次数,但为了达到相同的模型效果,需要增大学习率。但学习率一旦增大,又会引起模型的不收敛。为了解决这一矛盾,LARS算法就在各层上自适应的计算一个本地学习率用于更新本层的参数,这样能有效的提升训练的稳定性。目前利用LARS算法,腾讯公司使用65536的超大batch size能将ResNet50在ImageNet在4分钟完成训练,而谷歌使用32768的batch size使用TPU能将该时间缩短至2分钟。 ## 14.4 合理使用预训练网络 @@ -248,19 +240,23 @@ linear_cosine_decay(learning_rate, global_step, decay_steps, ​ 劣势在于,分类模型和检测模型之间仍然存在一定任务上的差异: -​ 1、检测模型能在多尺度上获取更高的收益; +​ 1、分类模型大部分训练于单目标数据,对同时进行多目标的捕捉能力稍弱,且不关注目标的位置,在一定程度上让模型损失部分空间信息,这对检测模型通常是不利的; -​ 2、分类模型大部分训练于单目标数据,对同时进行多目标的捕捉能力稍弱; +​ 2、域适应问题,若预训练模型(ImageNet)和实际检测器的使用场景(医学图像,卫星图像)差异较大时,性能会受到影响; -​ 3、分类模型并不关注目标的位置,在一定程度上让模型损失部分空间信息,这对检测模型通常是不利的。 +​ 3、使用预训练模型就意味着难以自由改变网络结构和参数限制了应用场合。 -### 14.4.5 目标检测中如何从零开始训练? +### 14.4.5 目标检测中如何从零开始训练(train from scratch)? -​ 参考14.15提到的使用预训练模型训练检测模型的优劣势,有两个方案在实际实现中可能会更有效。 +​ 结合FAIR相关的研究,我们可以了解目标检测和其他任务从零训练模型一样,只要拥有足够的数据以及充分而有效的训练,同样能训练出不亚于利用预训练模型的检测器。这里我们提供如下几点建议: -​ 方案一、通常二阶段检测模型并未实现真正完全端对端的训练,因此二阶段模型会更难以训练。所以一阶段检测模型相较起来更适合从零训练,参考DSOD,使用DenseNet使用更多层次的特征将更适应训练。 +​ 1、数据集不大时,同样需要进行数据集增强。 -​ 方案二、二阶段模型从零训练很难,而分类模型对于多目标、尺度并不敏感。因此仍然需要预训练模型的参数,这时借鉴DetNet训练一个专属于目标检测的模型网络,而参考分类模型的劣势,该专属网络应对多目标、尺度和位置拥有更强的适应性。 +​ 2、预训练模型拥有更好的初始化,train from scratch需要更多的迭代次数以及时间训练和优化检测器。而二阶段模型由于并不是严格的端对端训练,此时可能需要更多的迭代次数以及时间,而一阶段检测模型训练会相对更容易些(例如DSOD以ScratchDet及)。 + +​ 3、目标检测中train from scratch最大的问题还是batch size过小。所以可采取的策略是增加GPU使用异步batchnorm增大batch size,若条件限制无法使用更多GPU时,可使用groupnorm代替batchnorm + +​ 4、由于分类模型存在对多目标的捕捉能力弱以及对物体空间位置信息不敏感等问题,可借鉴DetNet训练一个专属于目标检测的模型网络,增强对多目标、尺度和位置拥有更强的适应性。 ## 14.5 如何改善 GAN 的性能 @@ -327,23 +323,76 @@ GAN常用训练技巧 ### 14.6.3 什么是神经网络架构搜索(NAS) -2015至2017年间,是CNN网络设计最兴盛的阶段,大多都是由学者人工设计的网络结构。这个过程通常会很繁琐。其主要原因在于对不同模块组件的组成通常是个黑盒优化的问题,此外,在不同结构超参数以及训练超参数的选择优化上非凸优化问题,或者是个混合优化问题,既有离散空间又有连续空间。NAS(Neural Architecture Search)的出现就是为了解决如何通过机器策略和自动化的方式设计出优秀高效的网络。而这种策略通常不是统一的标准,不同的网络结合实际的需求通常会有不同的设计,比如移动端的模型会在效率和精度之间做平衡。目前的网络架构搜索通常会分为三个方面,搜索空间,搜索策略以及评价预估。链接 | https://www.paperweekly.site/papers/2249 +2015至2017年间,是CNN网络设计最兴盛的阶段,大多都是由学者人工设计的网络结构。这个过程通常会很繁琐。其主要原因在于对不同模块组件的组成通常是个黑盒优化的问题,此外,在不同结构超参数以及训练超参数的选择优化上非凸优化问题,或者是个混合优化问题,既有离散空间又有连续空间。NAS(Neural Architecture Search)的出现就是为了解决如何通过机器策略和自动化的方式设计出优秀高效的网络。而这种策略通常不是统一的标准,不同的网络结合实际的需求通常会有不同的设计,比如移动端的模型会在效率和精度之间做平衡。目前,NAS也是AUTOML中最重要的部分。NAS通常会分为三个方面,搜索空间(在哪搜索),搜索策略(如何搜索)及评价预估。 + +- 搜索空间,即在哪搜索,定义了优化问题所需变量。不同规模的搜索空间的变量其对于的难度也是不一样的。早期由于网络结构以及层数相对比较简单,参数量较少,因此会更多的使用遗传算法等进化算法对网络的超参数和权重进行优化。深度学习发展到目前,模型网络结构越来越复杂,参数量级越来越庞大,这些进化算法已经无法继续使用。但若我们先验给定一些网络结构和超参数,模型的性能已经被限制在给定的空间,此时搜索的空间已变得有限,所以只需对复杂模型的架构参数和对应的超参数进行优化即可。 + +- 搜索策略, 即如何搜索,定义了如何快速、准确找到最优的网络结构参数配置的策略。常见的搜索方法包括:随机搜索、贝叶斯优化以及基于模型的搜索算法。其中主要代表为2017 年谷歌大脑的使用强化学习的搜索方法。 + +- 评价预估,定义了如何高效对搜索的评估策略。深度学习中,数据规模往往是庞大的,模型要在如此庞大的数据规模上进行搜索,这无疑是非常耗时的,对优化也会造成非常大的困难,所以需要一些高效的策略做近似的评估。 这里一般会有如下三种思路: + + 一、使用些低保真的训练集来训练模型。低保真在实际中可以用不同的理解,比如较少的迭代次数,用一小部分数据集或者保证结构的同时减少通道数等。这些方法都可以在测试优化结构时大大降低计算时间,当然也会存在一定的偏差。但架构搜索从来并不是要一组固定的参数,而是一种优秀的模型结构。最终选取时,只需在较优秀的几组结构中进行全集训练,进行择优选取即可。 -- 搜索空间,定义了优化问题的变量,网络结构和超参数的变量定义有所不同,不同的变量规模对于算法的难度来说也不尽相同。早期很多工作都是用以遗传算法为代表的进化算法对神经网络的超参数和权重进行优化,因为当时的神经网络只有几层,每层十几个神经元,也不存在复杂的网络架构,参数很有限,可直接进行优化。而深度学习模型一方面有着复杂的网络结构,另一方面权重参数通常都以百万到亿来计,进化算法根本无法优化。但换个思路,假如我们找到了一组网络架构参数和对应的超参数,深度学习模型的性能其实是由这组参数来控制和决定的,所以只需要对复杂模型的架构参数和对应的超参数进行优化即可。 + 二、使用代理模型。除了低保真的训练方式外,学者们提出了一种叫做代理模型的回归模型,采用例如插值等策略对已知的一些参数范围进行预测,目的是为了用尽可能少的点预测到最佳的结果。 -- 搜索策略, 搜索策略定义了使用怎样的算法可以快速、准确找到最优的网络结构参数配置。常见的搜索方法包括:随机搜索、贝叶斯优化、进化算法、强化学习、基于梯度的算法。其中,2017 年谷歌大脑的那篇强化学习搜索方法将这一研究带成了研究热点,后来 Uber、Sentient、OpenAI、Deepmind 等公司和研究机构用进化算法对这一问题进行了研究,这个 task 算是进化算法一大热点应用。 + 三、参数级别的迁移。例如知识蒸馏等。用已训练好的模型权重参数对目标问题搜索,通常会让搜索拥有一个优秀的起点。由于积累了大量的历史寻优数据,对新问题的寻优将会起到很大的帮助。 -- 评价预估,类似于工程优化中的代理模型(surrogate model),因为深度学习模型的效果非常依赖于训练数据的规模,大规模数据上的模型训练会非常耗时,对优化结果的评价将会非常耗时,所以需要一些手段去做近似的评估。 +### 14.6.4 NASNet的设计策略 - 一种思路是用一些低保真的训练集来训练模型,低保真在实际应用可以有多种表达,比如训练更少的次数,用原始训练数据的一部分,低分辨率的图片,每一层用更少的滤波器等。用这种低保真的训练集来测试优化算法会大大降低计算时间,但也存在一定的 bias,不过选择最优的架构并不需要绝对数值,只需要有相对值就可以进行排序选优了; +NASNet是最早由google brain 通过网络架构搜索策略搜索并成功训练ImageNet的网络,其性能超越所有手动设计的网络模型。关于NASNet的搜索策略,首先需要参考google brain发表在ICLR2017的论文《Neural Architecture Search with Reinforcement Learning》。该论文是最早成功通过架构搜索策略在cifar-10数据集上取得比较不错效果的工作。NASNet很大程度上是沿用该搜索框架的设计思想。 - 另一种主流思路是借鉴于工程优化中的代理模型,在很多工程优化问题中,每一次优化得到的结果需要经过实验或者高保真仿真(有限元分析)进行评价,实验和仿真的时间非常久,不可能无限制地进行评价尝试,学者们提出了一种叫做代理模型的回归模型,用观测到的点进行插值预测,这类方法中最重要的是在大搜索空间中如何选择尽量少的点预测出最优结果的位置; +NASNet的核心思想是利用强化学习对搜索空间内的结构进行反馈探索。架构搜索图如下,定义了一个以RNN为核心的搜索控制器。在搜索空间以概率p对模型进行搜索采样。得到网络模型A后,对该模型进行训练,待模型收敛得到设定的准确率R后,将梯度传递给控制器RNN进行梯度更新。 - 第三种主流思路是参数级别的迁移,用之前已经训练好的模型权重参数对target问题进行赋值,从一个高起点的初值开始寻优将会大大地提高效率。在这类问题中,积累了大量的历史寻优数据,对新问题的寻优将会起到很大的帮助,用迁移学习进行求解,是一个很不错的思路;另一种比较有意思的思路叫做单次(One-Shot)架构搜索,这种方法将所有架构视作一个 one-shot 模型(超图)的子图,子图之间通过超图的边来共享权重。 +![](.\img\ch14\NAS搜索策略.png) +​ 架构搜索策略流程 +RNN控制器会对卷积层的滤波器的尺寸、数量以及滑动间隔进行预测。每次预测的结果都会作为下一级的输入,档层数达到设定的阈值时,会停止预测。而这个阈值也会随着训练的进行而增加。这里的控制器之预测了卷积,并没有对例如inception系列的分支结构或者ResNet的跳级结构等进行搜索。所以,控制器需要进一步扩展到预测这些跳级结构上,这样搜索空间相应的也会增大。为了预测这些结构,RNN控制器内每一层都增加了一个预测跳级结构的神经元,文中称为锚点,稍有不同的是该锚点的预测会由前面所有层的锚点状态决定。 +![](.\img\ch14\RNN控制器.png) +​ RNN控制器 + +NASNet大体沿用了上述生成网络结构的机器,并在此基础上做了如下两点改进: + +1、先验行地加入inception系列和ResNet的堆叠模块的思想。其定义了两种卷积模块,Normal Cell和Reduction Cell,前者不进行降采样,而后者是个降采样的模块。而由这两种模块组成的结构可以很方便的通过不同数量的模块堆叠将其从小数据集搜索到的架构迁移到大数据集上,大大提高了搜索效率。 + +![](.\img\ch14\NASNet的RNN控制器.png) + +​ NASNet的RNN控制器 + +2、对RNN控制进行优化,先验性地将各种尺寸和类型的卷积和池化层加入到搜索空间内,用预测一个卷积模块代替原先预测一层卷积。如图,控制器RNN不在预测单个卷积内的超参数组成,而是对一个模块内的每一个部分进行搜索预测,搜索的空间则限定在如下这些操作中: + +​ • identity • 1x3 then 3x1 convolution +​ • 1x7 then 7x1 convolution • 3x3 dilated convolution +​ • 3x3 average pooling • 3x3 max pooling +​ • 5x5 max pooling • 7x7 max pooling +​ • 1x1 convolution • 3x3 convolution +​ • 3x3 depthwise-separable conv • 5x5 depthwise-seperable conv +​ • 7x7 depthwise-separable conv + +在模块内的连接方式上也提供了element-wise addition和concatenate两种方式。NASNet的搜索方式和过程对NAS的一些后续工作都具有非常好的参考借鉴意义。 + +### 14.6.5 网络设计中,为什么卷积核设计尺寸都是奇数 + +我们发现在很多大部分网络设计时都会使用例如3x3/5x5/7x7等奇数尺寸卷积核,主要原因有两点: + +- 保证像素点中心位置,避免位置信息偏移 +- 填充边缘时能保证两边都能填充,原矩阵依然对称 + +### 14.6.6 网络设计中,权重共享的形式有哪些,为什么要权重共享 + +权重共享的形式: + +- 深度学习中,权重共享最具代表性的就是卷积网络的卷积操作。卷积相比于全连接神经网络参数大大减少; +- 多任务网络中,通常为了降低每个任务的计算量,会共享一个骨干网络。 +- 一些相同尺度下的结构化递归网络 + +权重共享的好处: + +​ 权重共享一定程度上能增强参数之间的联系,获得更好的共性特征。同时很大程度上降低了网络的参数,节省计算量和计算所需内存(当然,结构化递归并不节省计算量)。此外权重共享能起到很好正则的作用。正则化的目的是为了降低模型复杂度,防止过拟合,而权重共享则正好降低了模型的参数和复杂度。 + +​ 因此一个设计优秀的权重共享方式,在降低计算量的同时,通常会较独享网络有更好的效果。 diff --git "a/ch15_GPU\345\222\214\346\241\206\346\236\266\351\200\211\345\236\213/readme.md" "b/ch15_GPU\345\222\214\346\241\206\346\236\266\351\200\211\345\236\213/readme.md" index d8afb155..b3b206dc 100644 --- "a/ch15_GPU\345\222\214\346\241\206\346\236\266\351\200\211\345\236\213/readme.md" +++ "b/ch15_GPU\345\222\214\346\241\206\346\236\266\351\200\211\345\236\213/readme.md" @@ -9,6 +9,6 @@ **贡献者(排名不分先后):** -冯宝宝 +内容贡献者可自加信息 ########################################################### diff --git "a/ch15_GPU\345\222\214\346\241\206\346\236\266\351\200\211\345\236\213/\347\254\254\345\215\201\344\272\224\347\253\240_\345\274\202\346\236\204\350\277\220\347\256\227\343\200\201GPU\345\217\212\346\241\206\346\236\266\351\200\211\345\236\213.md" "b/ch15_GPU\345\222\214\346\241\206\346\236\266\351\200\211\345\236\213/\347\254\254\345\215\201\344\272\224\347\253\240_\345\274\202\346\236\204\350\277\220\347\256\227\343\200\201GPU\345\217\212\346\241\206\346\236\266\351\200\211\345\236\213.md" index 69f81e4f..922e8762 100644 --- "a/ch15_GPU\345\222\214\346\241\206\346\236\266\351\200\211\345\236\213/\347\254\254\345\215\201\344\272\224\347\253\240_\345\274\202\346\236\204\350\277\220\347\256\227\343\200\201GPU\345\217\212\346\241\206\346\236\266\351\200\211\345\236\213.md" +++ "b/ch15_GPU\345\222\214\346\241\206\346\236\266\351\200\211\345\236\213/\347\254\254\345\215\201\344\272\224\347\253\240_\345\274\202\346\236\204\350\277\220\347\256\227\343\200\201GPU\345\217\212\346\241\206\346\236\266\351\200\211\345\236\213.md" @@ -8,23 +8,23 @@ ## 15.1 什么是异构计算? -异构计算是基于一个更加朴素的概念,”异构现象“,也就是不同计算平台之间,由于硬件结构(包括计算核心和内存),指令集和底层软件实现等方面的不同而有着不同的特性。异构计算就是使用结合了两个或者多个不同的计算平台,并进行协同运算。比如,比较常见的,在深度学习和机器学习中已经比较成熟的架构:CPU和GPU的异构计算;此外还有比较新的Google推出的协处理器TPU(Tensor Processing Unit),根据目的而定制的ASIC,可编程的FPGA等也都是现在在异构计算中使用比较多的协处理器。而本章中会着重介绍和深度学习共同繁荣的图形加算器,也就是常说的GPU。 +异构计算是基于一个更加朴素的概念,”异构现象“,也就是不同计算平台之间,由于硬件结构(包括计算核心和内存),指令集和底层软件实现等方面的不同而有着不同的特性。异构计算就是使用结合了两个或者多个不同的计算平台,并进行协同运算。比如,比较常见的,在深度学习和机器学习中已经比较成熟的架构:CPU和GPU的异构计算;此外还有比较新的Google推出的协处理器(TPU),根据目的而定制的ASIC,可编程的FPGA等也都是现在在异构计算中使用比较多的协处理器。而,本章中会着重介绍和深度学习共同繁荣的图形加算器,也就是常说的GPU。 ## 15.2 什么是GPGPU? -GPU,就如名字所包含的内容,原本开发的目的是为了进行计算机图形渲染,而减少对于CPU的负载。由于图像的原始特性,也就是像素间的独立性,所以GPU在设计的时候就遵从了“单指令流多数据流(SIMD)”架构,使得同一个指令(比如图像的某种变换),可以同时在多一个像素点上进行计算,从而得到比较大的吞吐量,才能使得计算机可以实时渲染比较复杂的2D/3D场景。在最初的应用场景里,GPU并不是作为一种通用计算平台出现的,直到2007年左右,一家伟大的公司——NVIDIA将GPU带到通用计算的世界里,使得其可以在相对比较友好的编程环境(CUDA/OpenCL)里加速通用程序成为了可能。从此之后,GPU通用计算(General Purpose Computing on GPU),即GPGPU,就成了学界和工业界都频繁使用的技术,在深度学习爆发的年代里,GPGPU成了推动这股浪潮非常重要的力量。 +GPU,就如名字所包含的内容,原本开发的目的是为了进行计算机图形渲染,而减少对于CPU的负载。由于图像的原始特性,也就是像素间的独立性,所以GPU在设计的时候就遵从了“单指令流多数据流(SIMD)”架构,使得同一个指令(比如图像的某种变换),可以同时在多一个像素点上进行计算,从而得到比较大的吞吐量,才能使得计算机可以实时渲染比较复杂的2D/3D场景。在最初的应用场景里,GPU并不是作为一种通用计算平台出现的,直到2007年左右,一家伟大的公司将GPU带到通用计算的世界里,使得其可以在相对比较友好的编程环境(CUDA/OpenCL)里加速通用程序成了可能。从此之后,GPU通用计算,也就是GPGPU就成了学界和工业界都频繁使用的技术,在深度学习爆发的年代里,GPGPU成了推动这股浪潮非常重要的力量。 ## 15.3 GPU架构简介 -GPU,图形显示芯片作为不同于CPU的设计逻辑和应用场景,有着非常不同的架构,理解 GPU 和 CPU 之间区别的一种简单方式是比较它们如何处理任务。CPU 由专为顺序串行处理而优化的几个核心组成,而 GPU 则拥有一个由数以千计的更小、更高效的核心(专为同时处理多重任务而设计)组成的大规模并行计算架构。本部分将简单介绍GPU究竟是如何架构,其中的计算核心有哪些特性。 +GPU,图形显示芯片作为不同于CPU的设计逻辑和应用场景,有着非常不同的架构,本部分将简单介绍GPU究竟是如何架构,其中的计算核心有哪些特性。 ### 15.3.1 如何通俗理解GPU的架构? 首先,下图简单地展示了几个GPU不同于CPU的特性: -* 计算核心: 图中的CPU i7-5960X,Intel的第五代Broadwell架构,其中包括了8个CPU核心(支持16线程),也就是理论上可以有16个不同的运算同时进行。除了8个核心计算单元,大部分的芯片面积是被3级缓存,内存和控制电路占据了。同样的,来自NVIDIA的GTX980GPU,在差不多的芯片面积上,大部分是计算单元,16个SM,也就是流处理单元,每个流处理单元中包含着128个CUDA计算核心,所以总共来说,有2048个GPU运算单元,相应地这颗GPU理论上可以在一个时钟周期内可以进行2048次单精度运算。 +* 计算核心: 图中的CPU,i7-5960,Intel的第五代Broadwell架构,其中包括了8个CPU核心(支持16线程),也就是理论上可以有16个不同的运算同时进行。除了8个核心计算单元,大部分的芯片面积是被3级缓存,内存和控制电路占据了。同样的,来自Nvidia的GTX980GPU,在差不多的芯片面积上,大部分是计算单元,16个SM,也就是流处理单元,每个流处理单元中包含着128个CUDA计算核心,所以总共来说,有2048个GPU运算单元,相应地这颗GPU理论上可以在一个时钟周期内可以进行2048次单精度运算。 ![CPU和GPU的简单架构对比图](./img/ch15/cpu_gpu.png) -* 计算核心频率:时钟频率,代表每一秒中内能进行同步脉冲次数,也是从一个侧面反映一个计算元件的工作速度。下图中对比了个别早期产品,比如Intel的X5650和几款NVIDIA的GPU。可以看出核心频率而言,CPU要远高于GPU。对于CPU而言,在不考虑能源消耗和制程工艺限制的情况下,追求更高的主频。但在GPU的设计中,采用了多核心设计,即使是提高一些频率,其实对于总体性能影像不会特别大。当然,其中还有能耗方面的考虑,避免发热过高,也进行了权衡。还有一个可能的原因是,在一个流处理器中的每个核心(CUDA核心)的运行共享非常有限的缓存和寄存器,由于共享内存也是有性能极限的,所以即使每个GPU核心频率提高,如果被缓存等拖累也是无法展现出高性能的。 +* 计算核心频率:时钟频率,代表每一秒中内能进行同步脉冲次数,也是从一个侧面反映一个计算元件的工作速度。下图中对比了个别早期产品,比如Intel的x5650和几款Nvidia的GPU。可以看出核心频率而言,CPU要远高于GPU。对于CPU而言,在不考虑能源消耗和制程工艺限制的情况下,追求更高的主频。但,在GPU的设计中,采用了多核心设计,即使是提高一些频率,其实对于总体性能影像不会特别大。当然,其中还有能耗方面的考虑,避免发热过高,也进行了权衡。还有一个可能的原因是,在一个流处理器中的每个核心(CUDA核心)的运行共享非常有限的缓存和寄存器,由于共享内存也是有性能极限的,所以即使每个GPU核心频率提高,如果被缓存等拖累也是无法展现出高性能的。 ![CPU简单信息](./img/ch15/cpu_specs.png) @@ -59,19 +59,11 @@ GPU整体的架构而言,某种意义上是同时支持以上两种并行模 深度学习在最近几年内出现的井喷现象背后也是GPU的存在和发展作为坚实的推动力量。 哪些场景使用GPU -在涉及大型矩阵运算的时候使用GPU可以显著加速处理速度,由于GPU架构的独特设计,针对矩阵运算可以实现高速并行计算,极大提高计算速度。 -一般在高性能计算,机器学习,深度学习,图像渲染等等场景中会比较多的使用矩阵运算,使用GPU可以显著加快处理速度。 -在一般的深度学习训练中,通常来说使用GPU比使用CPU都有10倍以上的速度提升,所以几乎所有深度学习的研究者几乎都是在使用GPU进行训练。 ImageNet的例子 ### 15.3.5 新图灵架构里的tensor core对深度学习有什么作用? -我们知道在深度学习中,矩阵-矩阵乘法运算(BLAS GEMM)是神经网络训练和推理的核心,并且矩阵乘法运算占据了所有计算量的大部分,而Tensor core就是为了解决这个问题而推出的,它的出现极大的提高了计算效率,大大加速了深度学习的计算速度,对深度学习的发展具有极大意义。 - -Tensor Core是Volta架构最重磅特性,是专门针对Deep Learning应用而设计的专用ASIC单元,实际上是一种矩阵乘累加的计算单元。(矩阵乘累加计算在Deep Learning网络层算法中,比如卷积层、全连接层等是最重要、最耗时的一部分。)Tensor Core可以在一个时钟周期内实现两个4×4矩阵乘法以及与另一个4×4矩阵加法。整个计算的个数,就是在一个时钟周期内可以实现64次乘和64次加。 - -所以Tensor Core就是为了矩阵乘法的加速而设计的,使用具有Tensor Core的GPU来进行深度学习的训练会极大的提高训练速度。 ## 15.4 CUDA 框架 @@ -86,10 +78,10 @@ Tensor Core是Volta架构最重磅特性,是专门针对Deep Learning应用而 GPU的性能主要由以下三个参数构成: 1. 计算能力。通常我们关心的是32位浮点计算能力。16位浮点训练也开始流行,如果只做预测的话也可以用8位整数。 -2. 显存大小。当模型越大,或者训练时的批量越大时,所需要的GPU显存就越多。 -3. 显存带宽。只有当显存带宽足够时才能充分发挥计算能力。 +2. 内存大小。当模型越大,或者训练时的批量越大时,所需要的GPU内存就越多。 +3. 内存带宽。只有当内存带宽足够时才能充分发挥计算能力。 -对于大部分用户来说,只要考虑计算能力就可以了。GPU显存尽量不小于4GB。但如果GPU要同时显示图形界面,那么推荐的显存大小至少为6GB。显存带宽通常相对固定,选择空间较小。 +对于大部分用户来说,只要考虑计算能力就可以了。GPU内存尽量不小于4GB。但如果GPU要同时显示图形界面,那么推荐的内存大小至少为6GB。内存带宽通常相对固定,选择空间较小。 下图描绘了GTX 900和1000系列里各个型号的32位浮点计算能力和价格的对比。其中价格为Wikipedia的建议价格。 @@ -97,16 +89,16 @@ GPU的性能主要由以下三个参数构成: 我们可以从图中读出两点信息: -1. 在同一个系列里面,价格和性能大体上成正比。但后发布的型号性价比更高,例如980 Ti和1080 Ti。 +1. 在同一个系列里面,价格和性能大体上成正比。但后发布的型号性价比更高,例如980 TI和1080 TI。 2. GTX 1000系列比900系列在性价比上高出2倍左右。 如果大家继续比较GTX较早的系列,也可以发现类似的规律。据此,我们推荐大家在能力范围内尽可能买较新的GPU。 ### 15.5.2 购买建议 ##### 首先给出一些总体的建议 -最好的GPU整体(小幅度):Titan Xp -综合性价比高,但略贵:GTX 1080 Ti,GTX 1070,GTX 1080 -性价比还不错且便宜:GTX 1060(6GB) +最好的GPU整体(小幅度):Titan Xp +综合性价比高,但略贵:GTX 1080 Ti,GTX 1070,GTX 1080 +性价比还不错且便宜:GTX 1060(6GB) 当使用数据集> 250GB:GTX Titan X(Maxwell) ,NVIDIA Titan X Pascal或NVIDIA Titan Xp @@ -124,29 +116,29 @@ GPU的性能主要由以下三个参数构成: 刚开始进行深度学习研究:从GTX 1060(6GB)开始。根据你下一步兴趣(入门,Kaggle比赛,研究,应用深度学习)等等,在进行选择。目前,GTX 1060更合适。 -想尝试下深度学习,但没有过多要求:GTX 1050 Ti(4或2GB) +想尝试下深度学习,但没有过多要求:GTX 1050 ti(4或2GB) -目前独立GPU主要有AMD和NVIDIA两家厂商。其中NVIDIA在深度学习布局较早,对深度学习框架支持更好。因此,目前大家主要会选择NVIDIA的GPU。 +目前独立GPU主要有AMD和Nvidia两家厂商。其中Nvidia在深度学习布局较早,对深度学习框架支持更好。因此,目前大家主要会选择Nvidia的GPU。 -NVIDIA有面向个人用户(例如GTX系列)和企业用户(例如Tesla系列)的两类GPU。这两类GPU的计算能力相当。然而,面向企业用户的GPU通常使用被动散热并增加了内存校验,从而更适合数据中心,并通常要比面向个人用户的GPU贵上10倍。 +Nvidia有面向个人用户(例如GTX系列)和企业用户(例如Tesla系列)的两类GPU。这两类GPU的计算能力相当。然而,面向企业用户的GPU通常使用被动散热并增加了内存校验,从而更适合数据中心,并通常要比面向个人用户的GPU贵上10倍。 -如果你是拥有100台机器以上的大公司用户,通常可以考虑针对企业用户的NVIDIA Tesla系列。如果你是拥有10到100台机器的实验室和中小公司用户,预算充足的情况下可以考虑NVIDIA DGX系列,否则可以考虑购买如Supermicro之类的性价比比较高的服务器,然后再购买安装GTX系列的GPU。 +如果你是拥有100台机器以上的大公司用户,通常可以考虑针对企业用户的Nvidia Tesla系列。如果你是拥有10到100台机器的实验室和中小公司用户,预算充足的情况下可以考虑Nvidia DGX系列,否则可以考虑购买如Supermicro之类的性价比比较高的服务器,然后再购买安装GTX系列的GPU。 -NVIDIA一般每一两年发布一次新版本的GPU,例如2016年发布的是GTX 1000系列,2018年发布的是RTX 2000系列。每个系列中会有数个不同的型号,分别对应不同的性能。 +Nvidia一般每一两年发布一次新版本的GPU,例如2017年发布的是GTX 1000系列。每个系列中会有数个不同的型号,分别对应不同的性能。 ## 15.6 软件环境搭建 深度学习其实就是指基于一套完整的软件系统来构建算法,训练模型。如何搭建一套完整的软件系统,比如操作系统的选择?安装环境中遇到的问题等等,本节做一个简单的总结。 ### 15.6.1 操作系统选择? 针对硬件厂商来说,比如NVIDIA,对各个操作系统的支持都是比较好的 ,比如Windows系列,Linux系列,但是由于Linux系统对专业技术人员比较友好,所以目前几乎所有的深度学习系统构建都是基于Linux的,比较常用的系统如Ubuntu系列,CentOS系列等等。 -在构建系统的时候,如何选择合适的操作系是一个刚刚入门深度学习的工作者面临的问题,在这里给出几点建议: -(1)刚刚入门,熟悉Windows系统,但是对Linux和深度学习都不太熟,这个时候可以基于windows系列系统来做入门学习。 -(2)简单了解Linux的使用,不太懂深度学习相关知识,可以直接基于Linux系统来搭建框架,跑一些开源的项目,慢慢深入研究学习。 -(3)熟悉Linux,不熟悉深度学习理论,毫无疑问,强烈推荐使用Linux系统,安装软件简单,工作效率高。 -总之一句话,如果不熟悉Linux,就先慢慢熟悉,最终还是要回归到Linux系统来构建深度学习系统。 +在构建系统的时候,如何选择合适的操作系是一个刚刚入门深度学习的工作者面临的问题,在这里给出几点建议: +(1)刚刚入门,熟悉Windows系统,但是对Linux和深度学习都不太熟,这个时候可以基于windows系列系统来做入门学习 +(2)简单了解Linux的使用,不太懂深度学习相关知识,可以直接基于Linux系统来搭建框架,跑一些开源的项目,慢慢深入研究学习 +(3)熟悉Linux,不熟悉深度学习理论,毫无疑问,强烈推荐使用Linux系统,安装软件简单,工作效率高 +总之一句话,如果不熟悉Linux,就先慢慢熟悉,最终还是要回归到Linux系统来构建深度学习系统 ### 15.6.2 常用基础软件安装? -目前有众多深度学习框架可供大家使用,但是所有框架基本都有一个共同的特点,目前几乎都是基于Nvidia的GPU来训练模型,要想更好的使用NVIDIA的GPU,cuda和cudnn就是必备的软件安装。 +目前有众多深度学习框架可供大家使用,但是所有框架基本都有一个共同的特点,目前几乎都是基于Nvidia的GPU来训练模型,要想更好的使用Nvidia的GPU,cuda和cudnn就是必备的软件安装。 1. **安装cuda** 上文中有关于cuda的介绍,这里只是简单介绍基于Linux系统安装cuda的具体步骤,可以根据自己的需要安装cuda8.0或者cuda9.0,这两种版本的安装步骤基本一致,这里以最常用的ubuntu 16.04 lts版本为例: 1. 官网下载,地址 diff --git "a/ch17_\346\250\241\345\236\213\345\216\213\347\274\251\343\200\201\345\212\240\351\200\237\345\217\212\347\247\273\345\212\250\347\253\257\351\203\250\347\275\262/17.8.1 NCNN\351\203\250\347\275\262.md" "b/ch17_\346\250\241\345\236\213\345\216\213\347\274\251\343\200\201\345\212\240\351\200\237\345\217\212\347\247\273\345\212\250\347\253\257\351\203\250\347\275\262/17.8.1 NCNN\351\203\250\347\275\262.md" new file mode 100644 index 00000000..08ef3e99 --- /dev/null +++ "b/ch17_\346\250\241\345\236\213\345\216\213\347\274\251\343\200\201\345\212\240\351\200\237\345\217\212\347\247\273\345\212\250\347\253\257\351\203\250\347\275\262/17.8.1 NCNN\351\203\250\347\275\262.md" @@ -0,0 +1,986 @@ +### 17.8.1 NCNN部署 + +##### 1.在电脑端使用ncnn实现分类(alexnet) + +s1,安装g++,cmake,protobuf,opencv + + + +s2,对源码进行编译 + +```shell +git clone https://github.com/Tencent/ncnn +$ cd +$ mkdir -p build +$ cd build +$ cmake .. +$ make -j4 +``` + + + +s3,准备caffe模型文件(alexnet) + +``` +deploy.prototxt +snapshot_10000.caffemodel +``` + +alexnet [deploy.prototxt](https://github.com/BVLC/caffe/tree/master/models/bvlc_alexnet), [caffemodel](http://dl.caffe.berkeleyvision.org/bvlc_alexnet.caffemodel) + + + +s4,使用ncnn转换工具将旧caffe版本的prototxt和caffemodel转新版本 + +将旧caffe版本的prototxt和caffemodel存放在caffe/build/tools目录下,执行如下命令完成转换 + +```shell +./upgrade_net_proto_text [old prototxt] [new prototxt] +./upgrade_net_proto_binary [old caffemodel] [new caffemodel] +``` + + + +s5,将deploy.prototxt中输入层替换成input层(如果只读取一张图片将dim设置为1) + +```protobuf +layer { + name: "data" + type: "Input" + top: "data" + input_param { shape: { dim: 1 dim: 3 dim: 227 dim: 227 } } +} +``` + + + +s6,使用caffe2ncnn工具将caffe model转成ncnn model + +```shell +./caffe2ncnn deploy.prototxt bvlc_alexnet.caffemodel alexnet.param alexnet.bin +``` + +在ncnn/build/tools目录下生成param和bin文件。 + + + +s7,对模型参数进行加密 + +```shell +./ncnn2mem alexnet.param alexnet.bin alexnet.id.h alexnet.mem.h +``` + +在ncnn/build/tools目录下生成.param、.bin和.h文件。 + +alexnet.param 网络的模型参数 + +alexnet.bin 网络的权重 + +alexnet.id.h 在预测图片的时候使用到 + + + +s8,编写pc端代码(参考https://blog.csdn.net/qq_36982160/article/details/79929869) + +```c++ +#include +#include +#include +#include"gesture.id.h" +#include "net.h" +//使用ncnn,传入的参数第一个是你需要预测的数据,第二个参数是各个类别的得分vector,注意传入的是地址,这样才能在这个函数中改变其值 +static int detect_squeezenet( float *data, std::vector& cls_scores) { + //实例化ncnn:Net,注意include "net.h",不要在意这时候因为找不到net.h文件而include报错,后文会介绍正确的打开方式 + ncnn::Net squeezenet; + + //加载二进制文件,也是照写,后面会介绍对应文件应该放的正确位置 + int a=squeezenet.load_param("demo.param"); + int b=squeezenet.load_param_bin("demo.bin"); + + //实例化Mat,前三个参数是维度,第四个参数是传入的data,维度的设置根据你自己的数据进行设置,顺序是w、h、c + ncnn::Mat in = ncnn::Mat(550, 8, 2, data); + + //实例化Extractor + ncnn::Extractor ex = squeezenet.create_extractor(); + ex.set_light_mode(true); + //注意把"data"换成你deploy中的数据层名字 + int d= ex.input("data", in); + + ncnn::Mat out; + //这里是真正的终点,不多说了,只能仰天膜拜nihui大牛,重点是将prob换成你deploy中最后一层的名字 + int c=ex.extract("prob", out); + + //将out中的值转化为我们的cls_scores,这样就可以返回不同类别的得分了 + cls_scores.resize(out.w); + for (int j=0; j cls_scores; //用来存储最终各类别的得分 + //这个函数的实现在上面,快去看 + detect_squeezenet(data, cls_scores); + for (int i = 0; i < cls_scores.size(); ++i) { + printf("%c : %f\n", a[i],cls_scores[i]); + } + + return 0; +} +``` + +代码是最简单的ncnn使用场景,可以根据自己需求加入代码。 + + + +s9,编译代码 + +(1) 编写CMakeLists.txt + +在CMakeLists.txt增加如下两行代码 + +```c +add_executable(demo demo.cpp) +target_link_libraries(demo ncnn) +``` + +CMakeLists.txt如下 + +``` +find_package(OpenCV QUIET COMPONENTS core highgui imgproc imgcodecs) +if(NOT OpenCV_FOUND) + find_package(OpenCV REQUIRED COMPONENTS core highgui imgproc) +endif() + +include_directories(${CMAKE_CURRENT_SOURCE_DIR}/../src) +include_directories(${CMAKE_CURRENT_BINARY_DIR}/../src) + +add_executable(squeezenet squeezenet.cpp) + +target_link_libraries(squeezenet ncnn ${OpenCV_LIBS}) + +add_executable(fasterrcnn fasterrcnn.cpp) +target_link_libraries(fasterrcnn ncnn ${OpenCV_LIBS}) + +add_executable(demo demo.cpp) +target_link_libraries(demo ncnn) + +add_subdirectory(ssd) +``` + +(2) 在ncnn根目录下CMakeLists.txt中编译examples语句的注释去掉 + +``` +############################################## + +# add_subdirectory(examples) +# add_subdirectory(benchmark) +add_subdirectory(src) +if(NOT ANDROID AND NOT IOS) +add_subdirectory(tools) +endif() +``` + +(3)ncnn/build目录下进行编译,生成demo可执行文件 + +``` +make +``` + + + +s10,执行 + +将生成的.param和.bin文件复制到ncnn/build/examples目录下,然后终端cd到ncnn/build/examples,执行: + +``` +./demo data_path1 data_path2 +``` + + + +##### 2. Win x64 (Visual Studio Community 2017) + +s1,安装Visual Studio Community 2017 + +``` +download Visual Studio Community 2017 from https://visualstudio.microsoft.com/vs/community/ +install it +Start → Programs → Visual Studio 2017 → Visual Studio Tools → x64 Native Tools Command Prompt for VS 2017 +``` + +s2,编译protobuf + +```powershell +download protobuf-3.4.0 from https://github.com/google/protobuf/archive/v3.4.0.zip +> cd +> mkdir build-vs2017 +> cd build-vs2017 +> cmake -G"NMake Makefiles" -DCMAKE_BUILD_TYPE=Release -DCMAKE_INSTALL_PREFIX=%cd%/install -Dprotobuf_BUILD_TESTS=OFF -Dprotobuf_MSVC_STATIC_RUNTIME=OFF ../cmake +> nmake +> nmake install +``` + +s3,编译ncnn库 + +```powershell +> cd +> mkdir -p build-vs2017 +> cd build-vs2017 +> cmake -G"NMake Makefiles" -DCMAKE_BUILD_TYPE=Release -DCMAKE_INSTALL_PREFIX=%cd%/install -DProtobuf_INCLUDE_DIR=/build-vs2017/install/include -DProtobuf_LIBRARIES=/build-vs2017/install/lib/libprotobuf.lib -DProtobuf_PROTOC_EXECUTABLE=/build-vs2017/install/bin/protoc.exe .. +> nmake +> nmake install + +pick build-vs2017/install folder for further usage +``` + + + +##### 3. Android端使用ncnn + +参考: + +https://blog.csdn.net/qq_33200967/article/details/82421089 + +https://blog.csdn.net/qq_36982160/article/details/79931741 + +s1,使用Android Studio安装ndk + +1)打开Android Studio,依次点击File->Settings->Appearance&Behavior->System Settings->Android SDK->SDK Tool,选中NDK,点击apply自动下载安装(如果安装成功会在SDK目录下生成ndk-bundle文件夹); + +2)配置ndk的环境变量 + + * 打开profile + + ```shell + sudo vim /etc/profile + ``` + + * 在profile文件末尾添加ndk路径 + + ```shell + export NDK_HOME=sdkroot/ndk-bundle + PATH=$NDK_HOME:$PATH + ``` + + * 保存退出,使用source命令使环境变量生效 + + ```shell + source /etc/profile + ``` + + * 验证ndk是否配置成功 + + ```shell + ndk-build -v + ``` + + + +s2,编译ncnn sdk + +通过如下命令编译ncnn sdk,会在ncnn/build-android下生成install文件夹,其中包括:include(调用ncnn所需的头文件)和lib(编译得到的ncnn库libncnn.a) + +```shell +mkdir build-android +cd build-android +cmake -DCMAKE_TOOLCHAIN_FILE=$ANDROID_NDK/build/cmake/android.toolchain.cmake \ + -DANDROID_ABI="armeabi-v7a" -DANDROID_ARM_NEON=ON \ + -DANDROID_PLATFORM=android-14 .. +make +make install +make package +``` + +参数设置请参考:https://github.com/Tencent/ncnn/wiki/cmake-%E6%89%93%E5%8C%85-android-sdk + +``` +ANDROID_ABI 是架构名字,"armeabi-v7a" 支持绝大部分手机硬件 +ANDROID_ARM_NEON 是否使用 NEON 指令集,设为 ON 支持绝大部分手机硬件 +ANDROID_PLATFORM 指定最低系统版本,"android-14" 就是 android-4.0 +``` + + + +s3,对源码进行编译 + +```shell +git clone https://github.com/Tencent/ncnn +$ cd +$ mkdir -p build +$ cd build +$ cmake .. +$ make -j4 +``` + + + +s4,准备caffe模型文件(alexnet) + +``` +deploy.prototxt +snapshot_10000.caffemodel +``` + +alexnet [deploy.prototxt](https://github.com/BVLC/caffe/tree/master/models/bvlc_alexnet), [caffemodel](http://dl.caffe.berkeleyvision.org/bvlc_alexnet.caffemodel) + + + +s5,使用ncnn转换工具将旧caffe版本的prototxt和caffemodel转新版本 + +将旧caffe版本的prototxt和caffemodel存放在caffe/build/tools目录下,执行如下命令完成转换 + +```shell +./upgrade_net_proto_text [old prototxt] [new prototxt] +./upgrade_net_proto_binary [old caffemodel] [new caffemodel] +``` + + + +s6,将deploy.prototxt中输入层替换成input层(如果只读取一张图片将dim设置为1) + +```protobuf +layer { + name: "data" + type: "Input" + top: "data" + input_param { shape: { dim: 1 dim: 3 dim: 227 dim: 227 } } +} +``` + +s7,使用caffe2ncnn工具将caffe model转成ncnn model + +```shell +./caffe2ncnn deploy.prototxt bvlc_alexnet.caffemodel alexnet.param alexnet.bin +``` + +在ncnn/build/tools目录下生成param和bin文件。 + + + +s8,对模型参数进行加密 + +```shell +./ncnn2mem alexnet.param alexnet.bin alexnet.id.h alexnet.mem.h +``` + +在ncnn/build/tools目录下生成.param、.bin和.h文件。 + +alexnet.param 网络的模型参数 + +alexnet.bin 网络的权重 + +alexnet.id.h 在预测图片的时候使用到 + + + +s9,开发安卓项目 + +(1)在Android Studio上创建一个NCNN1,并选择Include C++ support + +![这里写图片描述](https://img-blog.csdn.net/20180905204155999?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L3FxXzMzMjAwOTY3/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70) + +(2)在main目录下创建assets目录,并将alexnet.param、alexnet.bin、label.txt拷贝其中 + +(3)将include文件夹和 alexnet.id.h拷贝到cpp目录下 + +(4)在main目录下创建jniLibs/armeabi-v7a/目录,并将alexnet.id.h 拷贝其中 + +(5)在cpp文件夹下创建C++文件,用于加载模型和预测图片 + +```C++ +#include +#include +#include +#include +#include +// ncnn +#include "include/net.h" +#include "alexnet.id.h" +#include +#include +static ncnn::UnlockedPoolAllocator g_blob_pool_allocator; +static ncnn::PoolAllocator g_workspace_pool_allocator; +static ncnn::Mat ncnn_param; +static ncnn::Mat ncnn_bin; +static ncnn::Net ncnn_net; +extern "C" { +// public native boolean Init(byte[] param, byte[] bin, byte[] words); JNIEXPORT jboolean JNICALL +Java_com_example_ncnn1_NcnnJni_Init(JNIEnv *env, jobject thiz, jbyteArray param, jbyteArray bin) { + // init param + { + int len = env->GetArrayLength(param); + ncnn_param.create(len, (size_t) 1u); + env->GetByteArrayRegion(param, 0, len, (jbyte *) ncnn_param); int ret = ncnn_net.load_param((const unsigned char *) ncnn_param); + __android_log_print(ANDROID_LOG_DEBUG, "NcnnJni", "load_param %d %d", ret, len); + } + + // init bin + { + int len = env->GetArrayLength(bin); + ncnn_bin.create(len, (size_t) 1u); + env->GetByteArrayRegion(bin, 0, len, (jbyte *) ncnn_bin); + int ret = ncnn_net.load_model((const unsigned char *) ncnn_bin); + __android_log_print(ANDROID_LOG_DEBUG, "NcnnJni", "load_model %d %d", ret, len); + } + + ncnn::Option opt; + opt.lightmode = true; + opt.num_threads = 4; + opt.blob_allocator = &g_blob_pool_allocator; + opt.workspace_allocator = &g_workspace_pool_allocator; + + ncnn::set_default_option(opt); + + return JNI_TRUE; +} + +// public native String Detect(Bitmap bitmap); +JNIEXPORT jfloatArray JNICALL Java_com_example_ncnn1_NcnnJni_Detect(JNIEnv* env, jobject thiz, jobject bitmap) +{ + // ncnn from bitmap + ncnn::Mat in; + { + AndroidBitmapInfo info; + AndroidBitmap_getInfo(env, bitmap, &info); + int width = info.width; int height = info.height; + if (info.format != ANDROID_BITMAP_FORMAT_RGBA_8888) + return NULL; + + void* indata; + AndroidBitmap_lockPixels(env, bitmap, &indata); + // 把像素转换成data,并指定通道顺序 + in = ncnn::Mat::from_pixels((const unsigned char*)indata, ncnn::Mat::PIXEL_RGBA2BGR, width, height); + AndroidBitmap_unlockPixels(env, bitmap); + } + + // ncnn_net + std::vector cls_scores; + { + // 减去均值和乘上比例 + const float mean_vals[3] = {103.94f, 116.78f, 123.68f}; + const float scale[3] = {0.017f, 0.017f, 0.017f}; + + in.substract_mean_normalize(mean_vals, scale); + + ncnn::Extractor ex = ncnn_net.create_extractor(); + // 如果时不加密是使用ex.input("data", in); + ex.input(mobilenet_v2_param_id::BLOB_data, in); + + ncnn::Mat out; + // 如果时不加密是使用ex.extract("prob", out); + ex.extract(mobilenet_v2_param_id::BLOB_prob, out); + + int output_size = out.w; + jfloat *output[output_size]; + for (int j = 0; j < out.w; j++) { + output[j] = &out[j]; + } + + jfloatArray jOutputData = env->NewFloatArray(output_size); + if (jOutputData == nullptr) return nullptr; + + env->SetFloatArrayRegion(jOutputData, 0, output_size, reinterpret_cast(*output)); // copy + return jOutputData; + } +} +} +``` + +(6)在项目包com.example.ncnn1下,修改MainActivity.java中的代码 + +```java +package com.example.ncnn1; +import android.Manifest; +import android.app.Activity; +import android.content.Intent; +import android.content.pm.PackageManager; +import android.content.res.AssetManager; +import android.graphics.Bitmap; +import android.graphics.BitmapFactory; +import android.net.Uri; +import android.os.Bundle; +import android.support.annotation.NonNull; +import android.support.annotation.Nullable; +import android.support.v4.app.ActivityCompat; +import android.support.v4.content.ContextCompat; +import android.text.method.ScrollingMovementMethod; +import android.util.Log; +import android.view.View; +import android.widget.Button; +import android.widget.ImageView; +import android.widget.TextView; +import android.widget.Toast; + +import com.bumptech.glide.Glide; +import com.bumptech.glide.load.engine.DiskCacheStrategy; +import com.bumptech.glide.request.RequestOptions; + +import java.io.BufferedReader; +import java.io.FileNotFoundException; +import java.io.IOException; +import java.io.InputStream; +import java.io.InputStreamReader; +import java.util.ArrayList; +import java.util.Arrays; +import java.util.List; + +public class MainActivity extends Activity { + private static final String TAG = MainActivity.class.getName(); + private static final int USE_PHOTO = 1001; + private String camera_image_path; + private ImageView show_image; + private TextView result_text; + private boolean load_result = false; private int[] ddims = {1, 3, 224, 224}; + private int model_index = 1; + private List resultLabel = new ArrayList<>(); + private NcnnJni squeezencnn = new NcnnJni(); + + @Override + public void onCreate(Bundle savedInstanceState) { + super.onCreate(savedInstanceState); + setContentView(R.layout.activity_main); + + try { + initSqueezeNcnn(); + } catch (IOException e) { + Log.e("MainActivity", "initSqueezeNcnn error"); + } + + init_view(); + readCacheLabelFromLocalFile(); + } + + private void initSqueezeNcnn() throws IOException { + byte[] param = null; + byte[] bin = null; + + { + InputStream assetsInputStream = getAssets().open("mobilenet_v2.param.bin"); + int available = assetsInputStream.available(); + param = new byte[available]; + int byteCode = assetsInputStream.read(param); + assetsInputStream.close(); + } + + { + InputStream assetsInputStream = getAssets().open("mobilenet_v2.bin"); + int available = assetsInputStream.available(); + bin = new byte[available]; + int byteCode = assetsInputStream.read(bin); + assetsInputStream.close(); + } + + load_result = squeezencnn.Init(param, bin); + Log.d("load model", "result:" + load_result); + } + + // initialize view + private void init_view() { + request_permissions(); + show_image = (ImageView) findViewById(R.id.show_image); + result_text = (TextView) findViewById(R.id.result_text); + result_text.setMovementMethod(ScrollingMovementMethod.getInstance()); + Button use_photo = (Button) findViewById(R.id.use_photo); + + // use photo click + use_photo.setOnClickListener(new View.OnClickListener() { + @Override + public void onClick(View view) { + if (!load_result) { + Toast.makeText(MainActivity.this, "never load model", Toast.LENGTH_SHORT).show(); + return; + } + PhotoUtil.use_photo(MainActivity.this, USE_PHOTO); + } + }); + } + + // load label's name + private void readCacheLabelFromLocalFile() { + try { + AssetManager assetManager = getApplicationContext().getAssets(); + BufferedReader reader = new BufferedReader(new InputStreamReader(assetManager.open("synset.txt"))); + String readLine = null; + while ((readLine = reader.readLine()) != null) { + resultLabel.add(readLine); + } + reader.close(); + } catch (Exception e) { + Log.e("labelCache", "error " + e); + } + } + + @Override + protected void onActivityResult(int requestCode, int resultCode, @Nullable Intent data) { + String image_path; + RequestOptions options = new RequestOptions().skipMemoryCache(true).diskCacheStrategy(DiskCacheStrategy.NONE); + if (resultCode == Activity.RESULT_OK) { + switch (requestCode) { + case USE_PHOTO: + if (data == null) { + Log.w(TAG, "user photo data is null"); + return; + } + Uri image_uri = data.getData(); + Glide.with(MainActivity.this).load(image_uri).apply(options).into(show_image); + // get image path from uri + image_path = PhotoUtil.get_path_from_URI(MainActivity.this, image_uri); + // predict image + predict_image(image_path); + break; + } + } + } + + // predict image + private void predict_image(String image_path) { + // picture to float array + Bitmap bmp = PhotoUtil.getScaleBitmap(image_path); + Bitmap rgba = bmp.copy(Bitmap.Config.ARGB_8888, true); + + // resize to 227x227 + Bitmap input_bmp = Bitmap.createScaledBitmap(rgba, ddims[2], ddims[3], false); + try { + // Data format conversion takes too long + // Log.d("inputData", Arrays.toString(inputData)); + long start = System.currentTimeMillis(); + // get predict result + float[] result = squeezencnn.Detect(input_bmp); + long end = System.currentTimeMillis(); + Log.d(TAG, "origin predict result:" + Arrays.toString(result)); + long time = end - start; Log.d("result length", String.valueOf(result.length)); + // show predict result and time + int r = get_max_result(result); + String show_text = "result:" + r + "\nname:" + resultLabel.get(r) + "\nprobability:" + result[r] + "\ntime:" + time + "ms"; + result_text.setText(show_text); + } catch (Exception e) { + e.printStackTrace(); + } + } + + // get max probability label + private int get_max_result(float[] result) { + float probability = result[0]; + int r = 0; + for (int i = 0; i < result.length; i++) { + if (probability < result[i]) { + probability = result[i]; + r = i; + } + } + return r; + } + + // request permissions + private void request_permissions() { + List permissionList = new ArrayList<>(); + if (ContextCompat.checkSelfPermission(this, Manifest.permission.CAMERA) != PackageManager.PERMISSION_GRANTED) { + permissionList.add(Manifest.permission.CAMERA); + } + + if (ContextCompat.checkSelfPermission(this, Manifest.permission.WRITE_EXTERNAL_STORAGE) != PackageManager.PERMISSION_GRANTED) { + permissionList.add(Manifest.permission.WRITE_EXTERNAL_STORAGE); + } + + if (ContextCompat.checkSelfPermission(this, Manifest.permission.READ_EXTERNAL_STORAGE) != PackageManager.PERMISSION_GRANTED) { + permissionList.add(Manifest.permission.READ_EXTERNAL_STORAGE); + } + + // if list is not empty will request permissions + if (!permissionList.isEmpty()) { + ActivityCompat.requestPermissions(this, permissionList.toArray(new String[permissionList.size()]), 1); + } + } + + @Override + public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) { + super.onRequestPermissionsResult(requestCode, permissions, grantResults); + switch (requestCode) { + case 1: + if (grantResults.length > 0) { + for (int i = 0; i < grantResults.length; i++) { + int grantResult = grantResults[i]; + if (grantResult == PackageManager.PERMISSION_DENIED) { + String s = permissions[i]; + Toast.makeText(this, s + " permission was denied", Toast.LENGTH_SHORT).show(); + } + } + } + break; + } + } +} +``` + +(7)在项目的包com.example.ncnn1下,创建一个NcnnJni.java类,用于提供JNI接口,代码如下: + +```java +package com.example.ncnn1; + +import android.graphics.Bitmap; + +public class NcnnJni { + public native boolean Init(byte[] param, byte[] bin); + public native float[] Detect(Bitmap bitmap); + + static { + System.loadLibrary("ncnn_jni"); + } +} +``` + +(8)在项目的包com.example.ncnn1下,创建一个PhotoUtil.java类,这个是图片的工具类,代码如下: + +```java +package com.example.ncnn1; + +import android.app.Activity; +import android.content.Context; +import android.content.Intent; +import android.database.Cursor; +import android.graphics.Bitmap; +import android.graphics.BitmapFactory; +import android.net.Uri; +import android.provider.MediaStore; +import java.nio.FloatBuffer; + +public class PhotoUtil { + // get picture in photo + public static void use_photo(Activity activity, int requestCode) { + Intent intent = new Intent(Intent.ACTION_PICK); + intent.setType("image/*"); + activity.startActivityForResult(intent, requestCode); + } + + // get photo from Uri + public static String get_path_from_URI(Context context, Uri uri) { + String result; + Cursor cursor = context.getContentResolver().query(uri, null, null, null, null); + if (cursor == null) { + result = uri.getPath(); + } else { + cursor.moveToFirst(); + int idx = cursor.getColumnIndex(MediaStore.Images.ImageColumns.DATA); + result = cursor.getString(idx); + cursor.close(); + } + return result; + } + + // compress picture + public static Bitmap getScaleBitmap(String filePath) { + BitmapFactory.Options opt = new BitmapFactory.Options(); + opt.inJustDecodeBounds = true; + BitmapFactory.decodeFile(filePath, opt); + + int bmpWidth = opt.outWidth; + int bmpHeight = opt.outHeight; + + int maxSize = 500; + + // compress picture with inSampleSize + opt.inSampleSize = 1; + while (true) { + if (bmpWidth / opt.inSampleSize < maxSize || bmpHeight / opt.inSampleSize < maxSize) { + break; + } + opt.inSampleSize *= 2; + } + opt.inJustDecodeBounds = false; + return BitmapFactory.decodeFile(filePath, opt); + } +} +``` + +(9)修改启动页面的布局,修改如下: + +```xml + + + + + +