Style Transfer建模的想法

  1. 如果对模型没有什么想法,可以先随便试试,找找直观的感觉。例如:
    • 用不同的层计算content loss和style loss
    • 调整不同层在计算style loss时的权重
    • 在loss中使用不同的算法计算距离
    • 调整content loss和style loss的重要性
    • 生成图像的不同初始化
    • 使用不同的预训练模型
  2. 通过尝试使用不同的层计算content loss和style loss,发现使用的层越低(靠近输入层),对生成图像的影响越大。原来以为是因为低层的图像比较大,像素点多,所以产生的影响大,后来发现代码在计算过程是每一个层的计算结果是会根据这一层图像的大小做归一化的,所以不是这个原因。

  3. 物理上说,运动是相对的。算法上,变化也是相对的。如果把图像的像素值固定而迭代调整模型参数,可以得到特定用途的模型。亦反其道而行之,固定模型的参数,迭代调整图像的像素值,就可以得到特定要求的图像。用于迭代的变量和常量是可以相互转化的,这是一件神奇的事情。

  4. 通过固定参数而迭代调整图像的像素值,可以得到特定的图像,这是图像重构的基本原理。得到什么样的图像由loss function决定。如果loss funtion只包含content loss,就是对图像的内容重构,得到的图像看上去和原图很像。如果loss function只包含style loss,就是对图像的风格重构,得到的图像没有实际的内容,但是有类似原图像的纹理。

  5. 只做内容重构或者风格重构,且只基于模型某一层的输出做重构,可以看出不同的层对重构结果的影响。NN的较低层更关注细节而较高层更关注整体。表现在内容上,较低层的重构结果更精细准确而较高层则会模糊只能看出轮廓。表现在风格上,较高层的重构结果像素更连续而较低层相邻像素不连续。
  conv1_2 conv5_2
内容重构    
风格重构
  1. 卷积层的每一个channel,代表了对图像内容的某一个角度的特征。卷积层的channel之间的图像,代表了图像的不同特征之间的关系,这种关系构成了图像的风格。这里所谓的风格,实际上是纹理。

  2. 我尝试把真人照片迁移成漫画风格,但没有成功。我的理解是,这里所谓的风格,实际上是纹理,而漫画风格不是一种纹理,所以这种方法不适用。另外对style图像做风格重构得到图像算是最符合目标风格的图像了,也不是我想要的漫画风格,这也印证了我的想法。

  3. 原以为,直接使用内容图像C初始化生成图像G,能够更快地得到结果。实际不然,我是这样理解的:如果内容图像C、风格图像S都看作是高维空间中的某个点。期望的效果比较好的那些图像位于空间中某个不规则的区域D,且这个区域肯定在S和C之间。根据这些信息,通过loss function定义了目标图像E,也是C和S之间的某个点,如果content loss的权重较大,则E离C更近一点,反之则离G更近一点。但无法知道E是否在区域D中。通过调整参数,可能E会在离D比较近的位置。再定义生成图像的初始化值B,B可以放在与C或者S相同的位置,也可以是C或者S周围的某个位置,或者是空间中的任意位置。迭代过程实际上生成图像G从B出发向E移动的过程。迭代过程中离D最近的点就是能生成的最好的图像。

  4. 根据以上想法,我又尝试把B放在与S相同的位置,效果肯定不好,因此我们不关系S的内容,而是S的风格。所以应该先计算S的风格重构,然后把B放在S的风格重构图像的位置上。

  5. 还有以下问题需要解决:

    • 生成图像的清晰度不高,如果去噪?
    • 如果想要生成漫画风格的图像,要怎么做呢?
    • 用k.function实现提取keras模型某一层输出的方法,放在tape里面就会报错,只好用一种很低效的方法实现,怎么解决?
    • 生成的图像受那一张风格图像的影响很大,怎么生成具有某一类风格的图像?
    • 如果预训练模型的参数是随机的,是否能够用于图像重构?