提高驾驶技术:用GAN去除(爱情)动作片中的马赛克和衣服互联网+

雷锋网 2017-06-28 18:42
分享到:
导读

常见的生成式模型一般都会有一个用于产生样本的简单分布,自定义分布和生成这些样本的代码如下,根据要生成分布的概率密度函数。

作为一名久经片场的老司机,早就想写一些探讨驾驶技术的文章。这篇就介绍利用生成式对抗网络(GAN)的两个基本驾驶技能: 1) 去除(爱情)动作片中的马赛克 2) 给(爱情)动作片中的女孩穿(tuo)衣服 生成式模型上一篇《用GAN生成二维样本的小例子》中

  作为一名久经片场的老司机,早就想写一些探讨驾驶技术的文章。这篇就介绍利用生成式对抗网络(GAN)的两个基本驾驶技能:

  1) 去除(爱情)动作片中的马赛克

  2) 给(爱情)动作片中的女孩穿(tuo)衣服

  生成式模型上一篇《用GAN生成二维样本的小例子》中已经简单介绍了GAN,这篇再简要回顾一下生成式模型,算是补全一个来龙去脉。

  生成模型就是能够产生指定分布数据的模型,常见的生成式模型一般都会有一个用于产生样本的简单分布。例如一个均匀分布,根据要生成分布的概率密度函数,进行建模,让均匀分布中的样本经过变换得到指定分布的样本,这就可以算是最简单的生成式模型。比如下面例子:

  图中左边是一个自定义的概率密度函数,右边是相应的1w个样本的直方图,自定义分布和生成这些样本的代码如下:

  from functools import partial

  import numpy

  from MATplotlib import pyplot

  # Define a PDF

  x_samples = numpy.aranGE(-3, 3.01, 0.01)

  PDF = numpy.empty(x_samples.shape)

  PDF[x_samples < 0] = numpy.round(x_samples[x_samples < 0] + 3.5) / 3

  PDF[x_samples >= 0] = 0.5 * numpy.cos(numpy.pi * x_samples[x_samples >= 0]) + 0.5

  PDF /= numpy.sum(PDF)

  # CAlculate aPProximated CDF

  CDF = numpy.empty(PDF.shape)

  cuMUlated = 0

  for i in range(CDF.shape[0]):

  cumulated += PDF[i]

  CDF[i] = cumulated

  # Generate samples

  generate = partial(numpy.interp, xp=CDF, fp=x_samples)

  u_rv = numpy.random.random(10000)

  x = generate(u_rv)

  # Visualization

  fig, (ax0, ax1) = pyplot.subplots(ncols=2, fiGSize=(9, 4))

  ax0.plot(x_samples, PDF)

  ax0.axis([-3.5, 3.5, 0, numpy.max(PDF)*1.1])

  ax1.hist(x, 100)

  pyplot.show()

  对于一些简单的情况,我们会假设已知有模型可以很好的对分布进行建模,缺少的只是合适的参数。这时候很自然只要根据观测到的样本,学习参数让当前观测到的样本下的似然函数最大,这就是最大似然估计(MaximumLikelihoodEstimation):

  MLE是一个最基本的思路,实践中用得很多的还有KL散度(KullBAck�CLeibler divergence),假设真实分布是P,采样分布是Q,则KL散度为:

  从公式也能看出来,KL散度描述的是两个分布的差异程度。换个角度来看,让产生的样本和原始分布接近,也就是要让这俩的差异减小,所以最小化KL散度就等同于MLE。从公式上来看的话,我们考虑把公式具体展开一下:

  公式的第二项就是熵,先不管这项,用H(P)表示。接下来考虑一个小trick:从Q中抽样n个样本{x1, x2, ..., xn},来估算P(x)的经验值(empirical density function):

  其中δ()是狄拉克 δ函数,把这项替换到上面公式的P(x):

  因为是离散的采样值,所以

  中只有 x=xi 的时候狄拉克δ函数才为1,所以考虑 x=xi时这项直接化为 1:

  第一项正是似然的负对数形式。

  说了些公式似乎跑得有点远了,其实要表达还是那个简单的意思:通过减小两个分布的差异可以让一个分布逼近另一个分布。仔细想想,这正是GAN里面adversarial loss的做法。

  很多情况下我们面临的是更为复杂的分布,比如上篇文章中的例子,又或是实际场景中更复杂的情况,比如生成不同人脸的图像。这时候,作为具有universal approximation性质的神经网络是一个看上去不错的选择[1]:

  所以虽然GAN里面同时包含了生成网络和判别网络,但本质来说GAN的目的还是生成模型。从生成式模型的角度,Ian Goodfellow总结过一个和神经网络相关生成式方法的“家谱”[1]:

  在这其中,当下最流行的就是 GAN 和VariationalAutoEncoder(VAE),两种方法的一个简明示意如下[3]:

  本篇不打算展开讲什么是VAE,不过通过这个图,和名字中的autoencoder也大概能知道,VAE中生成的loss是基于重建误差的。而只基于重建误差的图像生成,都或多或少会有图像模糊的缺点,因为误差通常都是针对全局。比如基于MSE(Mean Squared Error)的方法用来生成超分辨率图像,容易出现下面的情况[4]:

  在这个二维示意中,真实数据分布在一个U形的流形上,而MSE系的方法因为loss的形式往往会得到一个接近平均值所在的位置(蓝色框)。

  GAN在这方面则完爆其他方法,因为目标分布在流形上。所以只要大概收敛了,就算生成的图像都看不出是个啥,清晰度常常是有保证的,而这正是去除女优身上马赛克的理想特性!

  马赛克->清晰画面:超分辨率(Super Resolution)问题说了好些铺垫,终于要进入正题了。首先明确,去马赛克其实是个图像超分辨率问题,也就是如何在低分辨率图像基础上得到更高分辨率的图像:

  视频中超分辨率实现的一个套路是通过不同帧的低分辨率画面猜测超分辨率的画面,有兴趣了解这个思想的朋友可以参考我之前的一个答案:如何通过多帧影像进行超分辨率重构?

  不过基于多帧影像的方法对于女优身上的马赛克并不是很适用,所以这篇要讲的是基于单帧图像的超分辨率方法。

  SRGAN说到基于GAN的超分辨率的方法,就不能不提到SRGAN[4]:《Photo-Realistic Single ImageSuper-Resolution Using aGenerativeAdversarialNetwork》。这个工作的思路是:基于像素的MSE loss往往会得到大体正确,但是高频成分模糊的结果。所以只要重建低频成分的图像内容,然后靠GAN来补全高频的细节内容,就可以了:

  这个思路其实和最早基于深度网络的风格迁移的思路很像(有兴趣的读者可以参考我之前文章瞎谈CNN:通过优化求解输入图像的最后一部分),其中重建内容的content loss是原始图像和低分辨率图像在VGG网络中的各个ReLU层的激活值的差异:

  生成细节adversarial loss就是GAN用来判别是原始图还是生成图的loss:

  把这两种loss放一起,取个名叫perceptual loss。训练的网络结构如下:

生成 分布 图像 GAN 样本
分享到:

1.TMT观察网遵循行业规范,任何转载的稿件都会明确标注作者和来源;
2.TMT观察网的原创文章,请转载时务必注明文章作者和"来源:TMT观察网",不尊重原创的行为TMT观察网或将追究责任;
3.作者投稿可能会经TMT观察网编辑修改或补充。


观点约架