这也是个困扰了我多年的问题:
loss = a * loss1 + b * loss2 + c * loss3 怎么设置 a,b,c?
我的经验是 loss 的尺度一般不太影响性能,除非本来主 loss 是 loss1,但是因为 b,c 设置太大了导致其他 loss 变成了主 loss。
实践上有几个调整方法:
手动把所有 loss 放缩到差不多的尺度,设 a = 1,b 和 c 取 10^k,k 选完不管了;
如果有两项 loss,可以 loss = a * loss1 + (1 - a) * loss2,通过控制一个超参数 a 调整 loss;
我试过的玄学躺平做法 loss = loss1 / loss1.detach() + loss2 / loss2.detach() + loss3 loss3.detach(),分母可能需要加 eps,一般效果不差(相当于在每一个 iteration 选定超参数 a, b, c,使得多个 loss 尺度完全一致);进一步 loss = loss1 + loss2 / (loss2 / loss1).detach() + loss3 / (loss3 / loss1).detach(),感觉比 loss 向 1 对齐更合理一点
某大佬告诉我,loss 就像菲涅尔透镜,纵使你能设计它的含义,也很难设计它的梯度。所以暴力一轮就躺平了。
我个人见解,很多 paper 设计一堆 loss 只是为了让核心故事更完整,未必强过调参。
其实这是目前深度学习领域被某种程度上忽视了的一个重要问题,
在近几年大火的multi-task learning,generative adversarial networks, 等等很多机器学习任务和方法里面都会遇到
,很多paper的做法都是暴力调参结果玄学……这里偷偷跟大家分享两个很有趣的研究视角从预测不确定性的角度引入Bayesian框架,
根据各个loss分量当前的大小自动设定其权重
。
有代表性的工作参见Alex Kendall等人的CVPR2018文章 Multi-Task Learning Using Uncertainty to Weigh Losses for Scene Geometry and Semantics,文章的二作Yarin Gal是Zoubin Ghahramani的高徒,近几年结合Bayesian思想和深度学习做了很多solid的工作。构建所有loss的Pareto,以一次训练的超低代价得到多种超参组合对应的结果。
有代表性的工作参见Intel在2018年NeurIPS(对,就是那个刚改了名字的机器学习顶会)发表的Multi-Task Learning as Multi-Objective Optimization 因为跟文章的作者都是老熟人,这里就不尬吹了,大家有兴趣的可以仔细读一读,干货满满。
一般都是多个loss之间平衡,即使是单任务,也会有weight decay项。
比较简单的组合一般通过调超参就可以
。对于比较复杂的多任务loss之间平衡,这里推荐一篇
通过网络直接预测loss权重的方法
[1]。以两个loss为例, 和 由网络输出,由于整体loss要求最小,所以前两项希望 越大越好,为防止退化,最后第三项则希望越小越好。当两个loss中某个比较大时,其对应的也会取较大值,使得整体loss最小化,也就自然处理量纲不一致或某个loss方差较大问题。
该方法后来被拓展到了物体检测领域[2],用于考虑每个2D框标注可能存在的不确定性问题。
[1] Alex Kendall, Yarin Gal, Roberto Cipolla. Multi-Task Learning Using Uncertainty to Weigh Losses for Scene Geometry and Semantics. CVPR, 2018.
[2] Yihui He, Chenchen Zhu, Jianren Wang, Marios Savvides, Xiangyu Zhang. Bounding Box Regression with Uncertainty for Accurate Object Detection. CVPR, 2019.
对于多任务的loss,最简单的方式是直接
将这两个任务的loss直接相加,得到整体的loss,这种loss计算方式的不合理之处是显而易见的
,不同任务loss的量级很有可能不一样,loss直接相加的方式有可能会导致多任务的学习被某个任务所主导或学偏。
当模型倾向于去拟合某个任务时,其他任务的效果往往可能受到负面影响,效果会相对变差(这是不是有一种零和博弈的感觉,当然也有跷跷板的感觉)。相对于loss直接相加的方式,这个loss函数对于每个任务的loss进行加权。这种方式允许我们手动调整每个任务的重要性程度;但是固定的w会一直伴随整个训练周期。这种loss权重的设置方式可能也是存在问题的,
不同任务学习的难易程度也是不同的
;且,不同任务可能处于不同的学习阶段,比如任务A接近收敛,任务B仍然没训练好等。这种固定的权重在某个阶段可能会限制了任务的学习。其实这是目前深度学习领域被某种程度上忽视了的一个重要问题,在近几年大火的multi-task learning,generative adversarial networks,等等很多机器学习任务和方法里面都会遇到,很多paper的做法都是暴力调参结果玄学。极端情况下,当某个任务的loss非常的大而其它任务的loss非常的小,此时多任务近似退化为单任务目标学习,网络的权重几乎完全按照大loss任务来进行更新,逐渐丧失了多任务学习的优势。
对于如何解决多个loss平衡的问题,可以查看以下几篇论文:
1、Multi-Task Learning Using Uncertainty to Weigh Losses for Scene Geometry and Semantics(基于任务不确定性)
2、GradNorm:Gradient Normalization for Adaptive(基于梯度更新)
3、另外还有研究将该问题看做多目标优化问题,这样做的好处是:在优化时将任务之间看做竞争关系,,而不是看作简单的线性组合,这样扩展了模型的适用范围。
一个代表性的工作:Multi-Task Learning as Multi-Objective Optimization4、Efficient Continuous Pareto Exploration in Multi-Task Learning
作者:Hanson
链接:https://www.zhihu.com/question/375794498/answer/1077922077
来源:知乎
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。
对于多任务学习而言,它每一组loss之间的数量级和学习难度并不一样,寻找平衡点是个很难的事情。我举两个我在实际应用中碰到的问题。第一个是多任务学习算法MTCNN,这算是人脸检测领域最经典的算法之一,被各家厂商魔改,其性能也是很不错的,也有很多版本的开源实现(如果不了解的话,传送门)。但是我在测试各种实现的过程中,发现竟然没有一套实现是超越了原版的。下图中是不同版本的实现,打了码的是我复现的结果。
不同版本mtcnn在FDDB上roc曲线这是一件很困扰的事情,参数、网络结构大家设置都大差不差。但效果确实是迥异。 clsloss表示置信度score的loss,boxloss表示预测框位置box的loss,landmarksloss表示关键点位置landmarks的loss。那么 这几个权值,究竟应该设置为什么样的才能得到一个不错的结果呢?其实有个比较不错的注意,就是只保留必要的那两组权值,把另外一组设置为0,比如 。为什么这么做?第一是因为关键点的回归在人脸检测过程中不是必要的,去了这部分依旧没什么大问题,也只有在这个假设的前提下才能进行接下来的实验。就比如这个MTCNN中的ONet,它回归了包括score、bbox、landmarks,我在用pytorch复现的时候,出现一些有意思的情况,就是将landmarks这条任务冻结后(即 ),发现ONet的性能得到了巨大的提升。能超越原始版本的性能。但是加上landmarks任务后( )就会对cls_loss造成影响,这就是一个矛盾的现象。而且和a、b、c对应的大小有很大关系。当设置成( )的时候关键点的精度真的是惨不忍睹,几乎没法用。当设置成( )的时候,loss到了同样一个数量级,landmarks的精度确实是上去了,但是score却不怎么让人满意。如果产生了这种现象,就证明了这个网络结构在设计的时候出现了一些缺陷,需要去修改backbone之后的multi-task分支,让两者的相关性尽量减小。或者是ONet就不去做关键点,而是选择单独的一个网络去做关键点的预测(比如追加一个LNet)。box的回归并不是特别受关键点影响,大部分情况box和landmarks是正向促进的,影响程度可以看做和score是一致的,box的精度即便下降了5%,它还是能框得住目标,因此不用太在意。上面这个实验意在说明,要存在就好的loss权重组合,那么你的网络结构就必须设计的足够好。不然你可能还需要通过上述的实验就验证你的网络结构。从多种策略的设计上去解决这中loss不均衡造成的困扰。和 @叶不知 讨论后,有一篇论文也可以提供参考https://arxiv.org/abs/1810.04002arxiv.org/abs/1810.04002第二个是我之前做过一点OCR方面的工作,这个是我对于表格框格式化方面做的工作,基本算原创工作。https://github.com/hanson-young/ocr-table-ssdgithub.com/hanson-young/ocr-table-ssd
改进版本的SSD表格检测算法是基于SSD改的,与原有SSD相比增加了一个预测heatmap的分支,算是一种attention机制的表现吧。改进后训练达到相同的精度和loss,SSD用时10小时,改进后的方法耗时仅需10-20min。在训练过程中如果两个分支一起训练,很难发挥网络的真正意义,并且收敛到不是很理想的地方,所以训练过程也挺重要的,在实验中,将原来的optimizer从SGD(不易收敛,可能和学习率有关)换到RMSProp:先冻结SSD网络,然后训练segmentation分支,到收敛再冻结segmentation分支进行SSD部分的训练,到收敛再将整个网络解冻训练到收敛,能达到比较好的效果
原图
预测结果
heatmap因为表格尺度的影响,不加入heatmap分支会导致图像被过分拉升,导致无法检测到表格框。加入heatmap后还有个好处就是为表格的对其提供了可能。
如果直接检测,对于一个矩形框来说,恐怕是会非常吃力的。如果heatmap -> 阈值分割 -> Sobel -> HoughLineP -> angle求出表格的倾斜角angle后,可以将原图和heatmap旋转统一的angle后concatenation,这样再接着跑SSD,对齐后的效果比较明显,解决了倾斜角度过大,带来bbox框过大的影响,详细见下图。
然后进行对齐工作
是不是能好很多
作者:郑泽嘉
链接:https://www.zhihu.com/question/375794498/answer/1056695768
来源:知乎
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。
Focal loss 会根据每个task的表现帮你自动调整这些参数的。我们的做法一般是先分几个stage 训练。stage 0 : task 0, stage 1: task 0 and 1. 以此类推。 在stage 1以后都用的是focal loss。
========== 没想到我也可以二更 ===============
是这样的。首先对于每个 Task,你有个 Loss Function,以及一个映射到 [0, 1] 的 KPI (key performance indicator) 。比如对于分类任务, Loss function 可以是 cross entropy loss,KPI 可以是 Accuracy 或者 Average Precision。对于 regression 来说需要将 IOU 之类的归一化到 [0, 1] 之间。KPI 越高表示这个任务表现越好。对于每个进来的 batch,每个Task_i 有个 loss_i。 每个Task i 还有个不同的 KPI: k_i。那根据 Focal loss 的定义,FL(k_i, gamma_i) = -((1 - k_i)^gamma_i) * log(k_i)。一般来说我们gamma 取 2。于是对于这个 batch 来说,整个 loss = sum(FL(k_i, gamma_i) * loss_i) 在直观上说,这个 FL,当一个任务的 KPI 接近 0 的时候会趋于无限大,使得你的 loss 完全被那个表现不好的 task 给 dominate。这样你的back prop 就会让所有的权重根据那个kpi 不好的任务调整。当一个任务表现特别好 KPI 接近 1 的时候,FL 就会是0,在整个 loss 里的比重也会变得很小。当然根据学习的速率不同有可能一开始学的不好的task后面反超其他task。 http://svl.stanford.edu/assets/papers/guo2018focus.pdf 这篇文章里讲了如何像momentum 一样的逐渐更新 KPI。由于整个 loss 里现在也要对 KPI 求导,所以文章里还有一些对于 KPI 求导的推导。当然我们也说了,KPI 接近 0 时,Loss 会变得很大,所以一开始训练的时候不要用focal loss,要确保网络的权重更新到一定时候再加入 focal loss。
来源:知乎
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。
深度学习
中,针对
loss
权重
的优化是重要的改进方向,许多
深度学习
应用都受益于具有多重回归和分类目标的多任务学习。每年的顶会都会出现不少关于
loss
优化的文章,还有大量的新
loss
定义方式,眼花缭乱。因此,一个
深度学习
任务中,一个
loss
往往有由
多个
loss
复合而成:
loss
= a*
loss
1+b*
loss
2+c*
loss
3...
如何调整这些
loss
权重
?超参.
在多目标多任务训练的网络中,如果最终的
loss
为有时为
多个
loss
的加权和,例如
loss
= a*
loss
_x+b*
loss
_y+c*
loss
_y+... ,这个问题在微信视频号视频推荐里也存在。任务需要对视频号的某个视频的收藏、点击头像、转发、点赞、评论、查看评论等进行多任务建模,也就产生了
多个
loss
。这里贴一下当时比赛的code:model.compile(
loss
= {'read_co...
笔者使用的是英伟达16系列显卡进行运行yolov8 v10 系列的代码,使用数据集进行训练的时候会出现文章标题的问题.三:找到ultralytics/engine/validator.py 文件。一:找到ultralytics/cfg/default.yaml文件。将self.args.half和force FP16这俩句注释掉.二:对照下文件里面的
参数
是否与下列相同,不同的话请改为和下列相同。此时在运行代码训练数据集就不会报错.
点击上方“视学算法”,选择加"星标"或“置顶”重磅干货,第一时间送达作者丨马东什么@知乎(已授权)来源丨https://zhuanlan.zhihu.com/p/36233...
问题:在一个端到端训练的网络中,如果最终的
loss
= a*
loss
1+b*
loss
2+c*
loss
3...,对于a,b,c这些超参的选择,有没有什么方法?链接:https://www.zhihu.com/question/375794498知乎高质量回答一、作者:Evan字节跳动研究员https://www.zhihu.com/question/375794498/answer/10527799...
个人感觉这是一个非常有意思的问题。之前在训练多任务
神经网络
的时候遇到过类似的问题,在我的问题中,损失函数有两项贡献,这两项 f 和 g,分别对应着分类损失和分割损失。随着学习的进行,这
两个
损失函数减小的速度很不一致。往往是一项减小的非常快,另一项减小的超级慢。看到这个问题的时候,我回想,应该可以对不同的损失项使用不同的学习率,即 Adaptive learning rate。其实 Adaptive...
*Box:**YOLOV5使用 GIOU
loss
作为bounding box的损失,Box推测为GIoU损失函数均值越小,方框越准。对于某个分类,综合了Precision和Recall的一个判断指标,F1-Score的值是从0到1的,1是最好,0是最差。**box_
loss
:**用于监督检测框的回归,预测框与标定框之间的误差(CIoU)。**cls_
loss
:**用于监督类别分类,计算锚框与对应的标定分类是否正确。**obj_
loss
:**用于监督grid中是否存在物体,计算网络的置信度。
在网络架构的设计中,最简单和最流行的方法是硬
参数
共享(HPS,LibMTL.architecture.HPS),如图1所示,其中编码器在所有任务之间共享,每个任务都有自己的编码器以及特定的解码器。(1)把各
loss
统一到同一个数量级上,其背后的原因是不同任务的不同损失函数尺度有很大的差异,因此需要考虑用权值将每个损失函数的尺度统一。和每个子任务之间的约束。而对于“不同网络部分梯度的数量级”问题,虽然梯度值相同,但不同的
loss
在task上的表现也是不同的,所以还是要找不同
loss
的合适
平衡
点。
损失函数(
Loss
Function)分为经验风险损失函数和结构风险损失函数,经验风险损失函数反映的是预测结果和实际结果之间的差别,结构风险损失函数则是经验风险损失函数加上正则项(L1或L2)。
深度学习
中的损失函数被用于模型
参数
的估计,通常作为学习准则与优化问题相联系,即通过最小化损失函数求解和评估模型。
机器学习
任务中的损失函数可以大体分为两种类型:回归损失和分类损失。在此基础上,在
深度学习
任务中又发展了很多不同的损失函数,由于在网络训练过程中损失函数指导着网络的学习,因此选择合适的损失函数也很重
点击上方“小白学视觉”,选择加"星标"或“置顶”重磅干货,第一时间送达来自 | 知乎地址 | https://www.zhihu.com/question/375794498编辑 | AI有道在一个端到端训练的网络中,如果最终的
loss
= a*
loss
1+b*
loss
2+c*
loss
3...,对于a,b,c这些超参的选择,有没有什么方法?作者:Evanhttps:/...
DFL损失的主要作用是用于校正模型在预测物体边界框时的误差,优化后的效果可以在一定程度上针对有些模糊或者焦点不集中的图片提升对象检测的精度。Box
Loss
直接依赖于模型预测的边界框与实际(或称为真值)边界框之间的距离。DFL损失是一个更高级的损失函数,目标是能在某些更复杂的情况下获得更好的性能,特别是针对一些难以边界框预测的目标。Box损失函数通常用于基本的目标检测任务,如Faster R-CNN, SSD等方法,Box损失是一个相对简单的损失函数,它主要计算预测的边界框与实际的边界框之间的位置偏差。