深度学习调参技巧总结

做dl也有一段时间了,积累了一些经验,也在网上看到一些别人的经验。
为了面试,结合知乎上面的问答,我也总结了一下,欢迎大家补充。

知乎 深度学习调参有哪些技巧?

一. 初始化
有人用normal初始化cnn的参数,最后acc只能到70%多,仅仅改成xavier,acc可以到98%。

二.从理解CNN网络以产生直觉去调参数的角度考虑,应该使用可视化
可视化(知乎用户 杨军)

1.Visualize Layer Activations
原则上来说,比较理想的layer activation应该具备sparse和localized的特点。
如果训练出的模型,用于预测某张图片时,发现在卷积层里的某个feature map的activation matrix可视化以后,基本跟原始输入长得一样,基本就表明出现了一些问题,因为这意味着这个feature map没有学到多少有用的东西。

2.Visualize Layer Weights
除了可视化隐藏层的activation以外,可视化隐藏层的模型weight矩阵也能帮助我们获得一些insights。

3.Embedding the Hidden Layer Neurons with t-SNE
这个方法描述起来比较直观,就是通过t-SNE[10]对隐藏层进行降维,然后以降维之后的两维数据分别作为x、y坐标(也可以使用t-SNE将数据降维到三维,将这三维用作x、y、z坐标,进行3d clustering),对数据进行clustering,人工review同一类图片在降维之后的低维空间里是否处于相邻的区域。

三.调参技巧 [知乎用户 Captain Jack]

  1. 刚开始, 先上小规模数据, 模型往大了放, 只要不爆显存, 能用256个filter你就别用128个. 直接奔着过拟合去. 没错, 就是训练过拟合网络, 连测试集验证集这些都可以不用.就是为了看整体训练流程没有错误,假如loss不收敛就要好好反思了。
  2. 观察loss胜于观察准确率
    准确率虽然是评测指标, 但是训练过程中还是要注意loss的. 你会发现有些情况下, 准确率是突变的, 原来一直是0, 可能保持上千迭代, 然后突然变1.
  3. Learning Rate设置合理
    • 太大: loss爆炸, 或者nan,或者loss根本不降而且维持较大值,因为有可能就是走过最优点了,每一步都走得太大
    • 太小: 半天loss没反映(但是, LR需要降低的情况也是这样, 这里可视化网络中间结果, 不是weights, 有效果, 俩者可视化结果是不一样的, 太小的话中间结果有点水波纹或者噪点的样子, 因为filter学习太慢的原因, 试过就会知道很明显)
    • 需要进一步降低了: loss在当前LR下一路降了下来, 但是半天不再降了.
    • 如果有个复杂点的任务, 刚开始, 是需要人肉盯着调LR的. 后面熟悉这个任务网络学习的特性后, 可以扔一边跑去了.
    • 如果上面的Loss设计那块你没法合理, 初始情况下容易爆, 先上一个小LR保证不爆, 等loss降下来了, 再慢慢升LR, 之后当然还会慢慢再降LR, 虽然这很蛋疼.
    • LR在可以工作的最大值下往小收一收, 免得ReLU把神经元弄死了. 当然, 我是个心急的人, 总爱设个大点的.
      4.简短的注意事项:
      预处理: -mean/std zero-center就够了, PCA, 白化什么的都用不上. 我个人观点, 反正CNN能学习encoder, PCA用不用其实关系不大, 大不了网络里面自己学习出来一个.
      shuffle, shuffle, shuffle.
      网络原理的理解最重要, CNN的conv这块, 你得明白sobel算子的边界检测
      Dropout, Dropout, Dropout(不仅仅可以防止过拟合, 其实这相当于做人力成本最低的Ensemble, 当然, 训练起来会比没有Dropout的要慢一点, 同时网络参数你最好相应加一点, 对, 这会再慢一点)
      .CNN更加适合训练回答是否的问题, 如果任务比较复杂, 考虑先用分类任务训练一个模型再finetune.无脑用ReLU(CV领域).
      无脑用3x3.无脑用xavier.
      LRN一类的, 其实可以不用. 不行可以再拿来试试看.现在一般就是用batch normalization了
      filter数量2^n.
      多尺度的图片输入(或者网络内部利用多尺度下的结果)有很好的提升效果.
      第一层的filter, 数量不要太少. 否则根本学不出来(底层特征很重要).
      sgd adam 这些选择上, 看你个人选择. 一般对网络不是决定性的. 反正我无脑用sgd + momentum.
      batch normalization我一直没用, 虽然我知道这个很好, 我不用仅仅是因为我懒. 所以要鼓励使用batch normalization.
      不要完全相信论文里面的东西. 结构什么的觉得可能有效果, 可以拿去试试.
      你有95%概率不会使用超过40层的模型
      .shortcut的联接是有作用的.暴力调参最可取, 毕竟, 自己的生命最重要. 你调完这个模型说不定过两天这模型就扔掉了.
      机器, 机器, 机器.
      Google的inception论文, 结构要好好看看.
      一些传统的方法, 要稍微了解了解. 我自己的程序就用过1x14的手写filter, 写过之后你看看inception里面的1x7, 7x1 就会会心一笑…因为这就是提取横竖条纹的。
      加data augmentation

知乎匿名用户:
感觉除了层数和每层隐节点的个数,也没啥好调的。其它参数,近两年论文基本都用同样的参数设定:迭代几十到几百epoch。sgd,mini batch size从几十到几百皆可。步长0.1,可手动收缩,weight decay取0.005,momentum取0.9。dropout加relu。weight用高斯分布初始化,bias全初始化为0。最后记得输入特征和预测目标都做好归一化。做完这些你的神经网络就应该跑出基本靠谱的结果,否则反省一下自己的人品。

你可能感兴趣的:(机器学习)