做食品分类这个需求,可能比大多数人想象的要麻烦不少。表面上看,这不就是给图片打个标签吗?但实际上,一道菜在不同光线、不同餐盘、不同摆盘角度下拍出来,差异非常大。更麻烦的是,标注一套可用的食品分类数据集,成本远比普通图像分类高——你很难让众包标注员准确区分“红烧肉”和“糖色收过了头的红烧肉”,也很难让不懂后厨的人分辨“酸辣土豆丝”和“醋溜土豆丝”之间的菜系差异。很多做餐饮视觉、智能食堂结算、营养摄入分析的项目,都卡在同一个地方:有大量监控摄像头和用户上传图片,但没有足够的专家标注。
我去年做了一个面向智能食堂场景的半监督食品分类系统,目标很直接:用少量人工标注数据,加上大量未标注的餐盘图片,训练一个能覆盖十几类常见菜品的分类模型。整套流程跑下来,我最大的感受是,半监督学习在这个场景下的价值不是“省掉标注”,而是“让已有的标注发挥更大的杠杆效应”。这篇文章就把我的完整思路、参数配置和踩过的坑记录下来,给正在做类似项目的朋友一个参考。
1. 半监督食品分类系统的问题拆解与方案选型
1.1 为什么食品分类特别适合半监督方案
先说说我为什么一开始就锁定半监督路线,而不是老老实实让人把两万张图全部标完。
食品分类有几个天然特点,让它和半监督学习非常契合。
第一,类别粒度细且存在大量“语义边界模糊”的样本。同样是“番茄炒蛋”,有的家庭做法偏甜,有的偏咸,有的加了葱花,有的加了番茄酱。如果类别体系按菜品名来定,那么标注人员必须拥有一套统一的判断标准,否则标注一致性会非常差。这种标注难度意味着:你花钱买来的标注,质量可能还不如不标。
第二,未标注数据几乎无限。食堂档口摄像头、外卖平台图片、用户随手拍、后厨备餐记录,到处都是食品图片。这些数据没有标签,但包含了丰富的场景变化、餐具变化、摆盘变化,恰恰是提升模型泛化能力最需要的东西。
第三,标注成本与标签价值之间存在严重的不对称。一张红烧肉的标注成本可能是普通动物分类图片的三到五倍,因为你需要让标注员理解“菜品级”的边界。而在半监督框架下,只需要标注一小部分“代表样本”,剩下的交给伪标签和一致性正则去利用,成本结构会健康很多。
第四,食品图像的背景结构相对固定。食堂餐盘、餐桌、打包盒,这些背景元素在未标注数据里大量重复出现。模型可以通过半监督学习轻松学到“餐盘边缘就是菜品边界”这类隐含知识,这比完全监督时需要人工标注 bounding box 或者 mask 要便宜得多。
1.2 方案选型:伪标签加一致性正则的组合
常见的半监督图像分类方案主要有几大类:伪标签法(self-training)、一致性正则法(Mean Teacher、FixMatch、MixMatch)、对比学习预训练加微调,以及最近比较热的基于 CLIP 之类大模型的零样本迁移。
我最终选择的路线是:伪标签 + 一致性正则 + 弱强增强,本质上接近 FixMatch 的简化版,但针对食品场景做了几个关键修改。
不用纯伪标签的原因很简单:伪标签法容易陷入“自我强化”的陷阱。模型第一次预测错了某个类,它会把错误的高置信度预测当成标签再训一遍,越训越偏。食品类别之间视觉相似度高,这种“错误共振”会被放大。你想象一下,模型把“锅包肉”和“糖醋里脊”之间反复横跳,两条类别的区分边界被错误伪标签反复冲刷,最后模型会直接把这两类合并。
一致性正则解决了这个问题的一部分。它的核心逻辑是:同一张未标注图片,经过轻微扰动后,模型对它的预测应该基本一致。不需要知道它是什么类别,只需要保证“你对它的看法是稳定的”。这种约束不会直接告诉模型“这是锅包肉”,而是让模型形成更平滑的决策边界,不会被个别高置信度错误样本带跑。
在 FixMatch 的基础上,我保留了“弱增强生成伪标签,强增强参与一致性学习”的框架:弱增强版本用于产生可靠的伪标签,强增强版本拿这些伪标签当学习目标。这个结构的好处是简单,工程上容易实现,而且对训练资源要求不高。选型时我没有上更复杂的 MixMatch,是因为 MixMatch 的“平均多次增强结果”在食品图像上计算量大,收益却不明显。
另外我加了一个比较务实的设计:不要一开始就上全部未标注数据。先用纯监督方式训练一个基础模型,预热十来个 epoch,让模型对食品类别有一个基本认知,然后再把未标注数据以伪标签的形式引入训练。这一点非常关键,后面我会详细展开。
2. 数据准备与初始模型训练
2.1 标注集设计:不是随便标,而是按“可解释类别体系”来标
半监督系统的效果上限,很大程度上取决于你手里那部分标注数据的质量,而不是未标注数据的数量。很多项目在标注阶段就埋了雷。我见过有人直接拿网上爬的菜谱图片当标注集,标签写得倒是花团锦簇,什么“鱼香肉丝(川菜版)”,结果训练出来的模型在实际食堂里第一个月就崩了,因为真实餐盘里的鱼香肉丝根本没有网图那么精致。
做食品分类的类别体系,我建议遵循一个原则:可解释、可区分、可复现。所谓可解释,就是你随便拿一张图问一个没参与项目的人,他也能根据你的类别定义大致判断该归到哪一类。所谓可区分,就是每个类别的视觉特征要有稳定的判别性,哪怕标注存在个体差异,也不至于把 A 类标成 B 类。所谓可复现,就是标注标准要写成文档,并且附上正例和反例图,标注团队遇到边界样本时有据可依。
我做的食堂场景,最终定了 14 个类别,包括“红烧肉”“番茄炒蛋”“清炒时蔬”“土豆丝”“红烧鱼块”“蒸蛋”“米饭”“面条”“汤品”等。没有做得太细,因为半监督学习在细粒度分类上的表现还不稳定,与其让模型去分“麻辣香锅微辣”和“麻辣香锅中辣”,不如先把大类做好。
每个类别的初始标注数量,我控制在 40 到 80 张之间。这个数量听起来不多,但要求是每张图都必须经过至少两轮人工审核。第一轮标注员初标,第二轮由懂后厨的人复核。标注图片的选择也有讲究,尽量覆盖不同光线、不同角度、不同盛具,而不是只挑拍得最好看的。半监督学习需要模型在真实分布上有平滑的决策边界,如果标注集全是“标准精美照”,那伪标签在“食堂实拍”上会不可靠。
2.2 数据采集与清洗:做半监督之前,先做减法
未标注数据的采集,我用的主要来源是食堂里部署的固定摄像头抓拍,以及用户在小程序端主动上传的餐品照片。总量大概有两万多张,但这个量级下数据清洗绝不能省。
有几个坑我帮大家提前踩了。
第一是重复图片。食堂摄像头每几秒抓一帧,同一份餐盘可能被拍到几十张高度相似的图。如果不做去重,模型会在重复样本上过拟合,伪标签也会被重复的高置信度样本带偏。我用的去重方案很简单:先用预训练模型提取特征,再做向量相似度聚类,相似度超过 0.95 的只保留一张。也可以直接用感知哈希,速度更快但粒度比较粗。对于食品图来说,embedding 级别的去重更稳,因为菜品形态的微小变化不该被当成完全重复。
第二是低质量图片。食堂摄像头经常有逆光、运动模糊、遮挡问题。我会先做一个清晰度过滤,把分辨率低于某个阈值、亮度方差过低的图片直接丢掉。这个环节不要吝啬,宁可让未标注集少一点,也别让一堆模糊图干扰一致性正则。
第三是“异物”图片。这个非常关键——摄像头里除了餐盘,还可能有手、打饭勺、托盘边缘、甚至一张宣传海报。如果未标注数据里混入大量非食品内容,伪标签会把它们强行归到某个食品类,造成灾难性的类别污染。我的做法是用一个现成的通用图像分类模型先粗筛一遍,排除明显不是食品的图片,再让后续的半监督模型自己 refine。这一步虽然听起来土,但实际省掉了后期大量排查时间。
2.3 初始模型训练:先做扎实的“满分下限”
半监督训练不是一上来就把未标注数据灌进去。我强烈建议:先只用手里的标注数据,训练一个尽量好的监督基线模型。这个模型有两个作用,一是作为后续半监督的起点,二是作为评价半监督增益的参照物。如果你连监督基线都做不好,加未标注数据只会放大错误。
我用的是 ImageNet 预训练的 ResNet-50,输入尺寸 224。没有一上来就用更大模型,因为食堂场景的类别差异主要靠纹理和颜色,ResNet-50 的容量在这个任务上已经够用。训练配置如下:
# 初始监督训练参考配置 config = { "model": "resnet50", "pretrained": True, "input_size": 224, "batch_size": 64, "epochs": 60, "optimizer": "SGD", "lr": 0.01, "lr_schedule": "cosine", "warmup_epochs": 5, "label_smoothing": 0.1, "weight_decay": 5e-4, "loss": "CrossEntropy" }几个细节值得展开。
标签平滑我开了 0.1。食品类别之间本来就存在模糊地带,标签平滑可以让模型不要对训练标签过于自信,后续生成伪标签时置信度会更合理。如果不开标签平滑,模型很容易在训练集上把某些样本预测到 0.999,但这种 0.999 在真实场景里完全不可靠。
学习率我用了 warmup 加 cosine 的经典组合。第一轮先让模型在低学习率下热身,避免预训练权重在初期被大步长更新破坏;后期学习率衰减到很低,让模型在局部最优附近稳定下来。训练 60 个 epoch 后,在验证集上的 top-1 accuracy 约为 78%,这个数字是后续所有半监督实验的“地板”。
还有一个容易被忽略的点:验证集一定要单独留出来,并且验证集的分布要与真实场景一致。我当时的验证集是从未标注池里随机抽了一层图像,再由人工标注得到的,而不是从训练标注集里切出来。这样可以防止模型仅仅记住了训练集的拍摄条件。
3. 半监督训练核心流程详解
3.1 伪标签生成:置信度阈值不是越高越好
半监督训练的第一步,是对未标注数据生成伪标签。我的做法是每个 training batch 动态生成:从未标注池里取一批图,先用当前模型预测,得到每个类别的概率分布,然后根据置信度筛选出合格的样本。
置信度阈值的设计是这里最核心的参数。我最初把阈值设为 0.95,发现利用率太低,每个 batch 里能用的未标注样本寥寥无几,训练和纯监督差不多。后来降到 0.8,利用率上来了,但错误伪标签也开始出现。最终我采用的策略是:阈值从 0.9 开始,每 10 个 epoch 下降 0.05,最低不低于 0.75。这样前中期用高阈值保证伪标签质量,后期模型逐渐变强,可以适当放松标准,把更多样本纳入训练。
这里还要注意一个非常关键的坑:伪标签分布监测。我遇到过一种情况:某几个类因为视觉上容易混淆,模型对它们的置信度普遍偏低,导致这些类的伪标签数量极少;相反,米饭、面条这类背景干净的类,伪标签数量爆炸式增长。这种不平衡会直接拖垮半监督训练。
解决方法是:每个 epoch 结束后,统计伪标签的类别分布,并设置每类伪标签数量上限。超出上限的样本先丢弃,留到下一轮再参与训练。打个比方,就像食堂打饭——菜品种类再多,每个窗口出菜量也要控制,不能让一个窗口把后厨的菜全占用了。
3.2 一致性正则:弱增强与强增强的分工
一致性正则的核心,是让同一个样本的不同增强版本得到一致的预测。我在实现时,把增强分成两条分支。
弱增强分支用来生成伪标签。这里的弱增强包括随机裁剪、水平翻转、轻微的亮度抖动。我特别强调“轻微”——食品分类里颜色是强判别特征,红烧肉的焦糖色、清炒时蔬的翠绿色,一旦增强幅度过大,把颜色改得不自然,伪标签的可靠性会直线下降。网上很多通用图像分类的增强配置直接把颜色扰动开到很强,比如随机改变色相,这在食品场景里容易翻车。我会把颜色增强的幅度限制在亮度 ±0.1、对比度 ±0.1、饱和度 ±0.1 之内,色相不动。
强增强分支用来做学习目标。这里我用了 RandAugment,但同样做了食品场景适配。RandAugment 的默认配置里有大量几何变换和颜色变换,直接套用会过度扭曲食品形态。比如“旋转 90 度”会让一份盖饭看起来完全不像饭,“颜色反转”更是直接摧毁食品语义。我的做法是:只保留裁剪、平移、缩放、轻微旋转这些几何增强,颜色类增强全部关掉,并且将增强幅度从默认的 9 级下调到 5 级。
对于一个食品分类项目,增强策略的核心不是“越强越好”,而是“在保留可辨识性的前提下尽量增加多样性”。你需要让模型看到同一个菜品在不同角度、不同构图下的样子,而不是看到一张完全变形的抽象色块。
3.3 损失组合与动态权重
半监督训练的总损失包含三部分:监督损失、无监督一致性损失、以及我额外加的一个小惩罚项。公式上很简单:
total_loss = sup_loss + lambda_u * unsup_loss + lambda_reg * reg_loss监督损失就是标注数据上的交叉熵。无监督一致性损失,是强增强预测和伪标签之间的交叉熵。回归损失我用了“伪标签类别分布的熵正则”,这个需要稍微解释一下。
如果没有这个正则,模型会倾向于把所有低置信度未标注样本都预测到几个容易分类的头部类别(比如米饭),因为这样能让一致性损失降得更低。这个现象在半监督训练中极其常见:模型会找到一条“偷懒”的路径,把模糊样本全部归到高频类,换来表面上的损失下降。熵正则的作用,是鼓励伪标签的类别分布整体上均匀一些,不要出现某个类独大的情况。
lambda_u的权重控制也非常重要。我采用的是线性 warmup:前 10 个 epochlambda_u从 0 缓慢升到 1。如果一开始就把无监督损失开到满,模型的前几次更新会被大量伪标签主导,而这时伪标签的质量还不可靠。我曾经试过一股脑把lambda_u设为 1,结果训练到第 30 个 epoch 时准确率直接崩了,后来逐步暖启动才恢复正常。
还有一个工程实现上的细节:EMA(指数滑动平均)。我没有直接用 student 模型的权重来生成伪标签,而是维护了一个 teacher 模型,它是 student 权重的指数移动平均:
teacher_weight = decay * teacher_weight + (1 - decay) * student_weightdecay设为 0.999。这样做的好处是,teacher 模型的权重是学生模型多个版本的平均值,预测会更稳定,生成的伪标签不容易因为单次更新而剧烈震荡。你可以理解为:学生模型负责“探索”,teacher 模型负责“总结”,伪标签由那个见多识广的总结者来出,比让学生自己给自己出题靠谱得多。
3.4 训练计划与模型评估
整个半监督训练的完整时间线,我整理成了下面这张表:
| 阶段 | epoch 范围 | 使用数据 | 训练目标 |
|---|---|---|---|
| 冷启动 | 1-10 | 仅标注集 | 学习基础特征 |
| 半监督稳定期 | 11-70 | 标注集 + 伪标签 | 利用未标注数据 |
| 微调收敛期 | 71-100 | 标注集 + 高质量伪标签 | 提升决策边界精细度 |
冷启动阶段只跑监督损失,让模型先具备最基本的分类能力。到了半监督阶段,伪标签置信度阈值逐渐放开,lambda_u逐渐升高。最后 30 个 epoch,我反而会调高阈值到 0.9,只保留最可靠的伪标签参与微调。这样做能防止训练后期梯度噪声过大,保证最终收敛到一个 sharp 的极小值。
评估指标上,我强烈建议不要只用 accuracy。食品类别天然不平衡,米饭、馒头这类主食占大头,如果只看 accuracy,模型只要把所有图都判成主食,数字也不会太难看。我采用的是 macro-F1 作为主指标,同时监控每一类的 precision 和 recall。只有当所有类别的 recall 都超过某个阈值时,我才会认为模型合格。
最终模型的 macro-F1 比纯监督基线提升了 4.3 个百分点,而 top-1 accuracy 只提升了 2.1 个百分点。这个对比很能说明问题:半监督的收益主要体现在尾部类别和模糊样本上,而不是头部高频类。
4. 常见问题排查与避坑记录
4.1 伪标签噪声太大,模型越训越偏
半监督训练最令人头疼的故障模式,就是 loss 明明在下降,但验证集准确率却突然大幅下跌。我遇到过一次:训练到第 34 个 epoch 时,模型对“红烧肉”的 recall 突然从 0.7 掉到 0.3,而且后面几个 epoch 都没有恢复。
排查下来,原因是有一批伪标签出错了。食堂窗口当天推出了一款新品,看起来像红烧肉但其实是某种卤味拼盘,摄像头拍了一批图。模型对这批图的置信度很高(0.95 以上),于是它们被打上了“红烧肉”的伪标签,参与了训练。由于这批图的分布和真实红烧肉有明显差异,模型学到了错误的关联,导致对真正的红烧肉反而不再敏感。
这个问题的根源不是伪标签本身,而是置信度阈值无法区分“可靠的错误”和“不可靠的正确”。模型对一个错误认知非常自信时,伪标签不但无益,反而有害。
我的解决方法是加入“伪标签类别分布软上限”。每个 epoch 开始前,统计上一轮的伪标签预测类别分布,如果某个类别的数量超过均匀分布的某个倍数,就把该类别中置信度最低的那些样本剔除。这相当于给每个类别一个预算,避免某个类被异常数据集体污染。
4.2 模型对长尾类别直接放弃
食堂场景里的长尾现象非常典型:米饭、面条几乎每顿都出现,而“蒸蛋”“清炒时蔬”这类菜品出现频率低得多。半监督训练会自发地放大这种不平衡,因为头部类别有大量高置信度伪标签,模型越训越擅长它们,尾部类别则因为伪标签数量少而逐渐被忽略。
这不是一个能靠调参完全解决的问题。我用了三管齐下的措施。
第一,在损失函数中为尾部类别增加权重。这里我给监督损失加了简单的类别权重,按1 / sqrt(class_freq)计算,而不是常见的1 / class_freq,因为衰减太快会导致模型在头部类别上表现骤降。
第二,对伪标签做类别平衡采样。每个 batch 里,未标注样本的伪标签类别会参与一个采样权重计算,让尾部类别在训练中出现的频率更高。这不能改变伪标签的总量,但能让尾部类别的梯度更新更频繁。
第三,为尾部类别人工补充标注。这也是最有效的一招。我挑出了伪标签数量最少的三个类别,每个类别人工标注了 30 张额外图片,加入监督损失一起训练。这个操作让总体 macro-F1 直接涨了 1.5 个点。
4.3 半监督效果不佳,甚至不如纯监督
有朋友问过我:如果未标注数据和标注数据分布差异太大,半监督是不是会有害?
确实是。我有一个具体的例子。当时团队想加入外卖场景的未标注图片来增强多样性,但这些图片大多带有外卖平台的放置角度:俯拍、盒子边缘清晰、背景是桌面纹理。而标注集里主要是食堂餐盘的照片:侧面拍摄、背景是餐台。两者的分布差异太大,半监督模型强行将外卖图片的决策边界向食堂方向拉,反而让食堂场景的模型表现变差。
这个问题的本质是:伪标签方法假设未标注数据与标注数据来自同一个label space和同一个visual domain。当这个假设不成立时,模型会把错误的域间迁移当成学习目标。
解决思路是分层处理。如果你的未标注数据里有明显不同的子域,可以先用聚类把数据分成几个域,分别训练域内的一致性正则,或者至少给不同域设置不同的伪标签置信度阈值。我在后续迭代中,只选用了与标注集分布相近的食堂摄像头数据作为未标注池,外卖图片则暂时放在一边,等有条件做域适应时再单独处理。
4.4 训练过程准确率反复横跳
半监督训练相比全监督更容易出现波动,因为伪标签本身是动态变化的。loss 曲线像心电图,一会儿高一会儿低,并不一定是坏事,但也需要区分是正常波动还是发散前兆。
我的经验是:当伪标签置信度阈值下降后,准确率会在 2 到 3 个 epoch 内出现小幅度波动,这是正常的,说明模型正在吸收新的样本。但如果你看到某个类别的准确率连续 5 个 epoch 单边下降,那就是异常,需要立刻回滚到上一个 checkpoint,调高阈值或降低lambda_u。
我还习惯在每个 epoch 结束后打印一个伪标签质量快报,包括:使用了多少未标注样本、伪标签的类别分布 top1/top2(我指的是分布最高的两个类,不是模型 predicts 的 top2)、被拒绝的低置信度样本比例。如果伪标签类别分布开始出现明显的单极化,我会直接停止训练,调整配置后再继续。这个习惯让我在多个项目里少走了很多弯路。
5. 从实验到落地:部署与迭代经验
5.1 推理部署与未知类拒识
模型训练完成后,进入部署环节,又有一批新的问题。食品分类的落地场景很现实:食堂收银台前面一个摄像头,你要在几百毫秒内判断这份餐盘里是哪个菜。我不能在每条路线上依赖 GPU,所以最终选择了 ONNX Runtime 加 CPU 推理,模型从 ResNet-50 蒸馏到一个更小的 EfficientNet-B0 版本。
蒸馏的过程也可以用半监督的思路来做:大模型(teacher)对无标注数据生成预测,小模型(student)用这些预测来学习。这一步让模型大小从 90MB 压缩到 20MB,准确率只损失了 0.8 个百分点。
部署中最重要的一个细节,是未知类拒识。真实食堂里,顾客可能往餐盘里放一张纸巾、一个手机、或者一份市场新买的零食。如果模型强行把这些归到 14 个已知类别里,会闹出大问题。我的策略是:对模型的 softmax 输出做一个阈值判断,最高概率低于 0.5 或与第二高概率差距小于 0.1 时,直接输出“未知”,让系统走人工兜底流程。这个阈值需要在真实场景里调,我试过 0.6,效率太低;试过 0.4,误拒率太高;最终卡在 0.5,人工复核率在 5% 左右,可以接受。
5.2 数据闭环:半监督系统的持续进化
半监督系统不是一次性训练完就结束了。我的实践里,“数据闭环”才是它真正的价值所在。
在部署后,模型每次推理都会保留一张结果图。每周我会把模型输出中置信度低于 0.7 的样本打出来,人工快速标记一遍。这些“低置信度边缘样本”是最有价值的,因为它们是模型尚未理解的困难区域,人工标记后直接加入标注集,等于每次都在用模型自己发现盲区。
高置信度的样本,我也不会自动信任。每两周从中随机抽 5%,人工快速复核一遍,主要看有没有标注翻转。这个复核环节曾经让我发现了一个数据 bug:某类菜品的色调在特定灯光下发生了偏移,导致模型对同类菜品预测不稳定。如果只看 loss,根本发现不了这个问题;而人工复核之后重新训练,模型在当月的新数据上误判率下降了 30% 左右。
5.3 与标注团队协作的方式
最后分享一下关于“人”的经验。很多半监督教程都只讲模型,不讲工程协作,但我觉得在食品分类这种需要领域知识的场景里,人是整个系统里不可替代的一环。
我的做法是:把人工标注分成两层。第一层是“快速标注员”,负责给未标注数据打预标签,不需要太准确,主要用于给半监督模型提供初始伪标签候选。第二层是“复核专家”,通常是真正懂后厨的人,负责审核第一层的标签、处理边界案例、制定类别定义文档。半监督训练的目的,是让“复核专家”的时间尽量花在真正困难、真正值得人工介入的样本上,而不是花在那些一眼就能看出来的米饭、面条上面。
项目管理上,我用了一个非常朴素但有效的指标:人工复核通过率。每周统计从低置信度样本池里抽出的 200 张图,人工给的真实类别与模型预测的一致率。这个指标会随着半监督迭代一次次上升,直到稳定在某个阈值附近。当它不再上升时,说明模型已经榨干了这个数据分布下的信息,你需要引入新的数据源或调整类别体系,而不是继续调lambda_u。
我个人在实际操作中的体会是:半监督食品分类系统,本质上不是让你少干活,而是让你把精力从“大量重复标注”转移到“少量高质量标注”和“错误模式排查”上。伪标签和一致性正则只是工具,真正决定系统上限的,是你对食品视觉特征的理解决策。如果你正准备上手类似的项目,我的建议是:第一,把标注数据质量控制在“少而精”;第二,训练时盯紧类别分布,不要只盯 loss;第三,部署后一定要做数据闭环,让模型持续吸收真实场景里冒出来的新样本。这三件事做好了,半监督食品分类这个项目才有机会真正落地,而不是停在实验报告里。
最后再分享一个小技巧。训练结束后,记得把训练集中模型分类置信度最高的一批图片打印出来看一遍。我每次这么做,都会发现几个“标签画错了但模型依然学对了”的样本,也偶尔会发现“模型用背景特征偷答案”的极端案例。修正这些标注错误再去重训一轮,往往还有一次免费的涨点机会。