| 导语 开源社区这一年半来,在大模型领域做了大量的探索,总结了很多有价值的经验。Llama 3.1的技术报告使用的方法,可以认为是目前开源社区的集大成者。对LLama 3.1技术报告的解读,可以了解现在社区训练大模型最成熟、最先进的技术是什么样的,在实际训练模型的时候具有重要意义。
自从去年年初,大模型由于其惊人的效果,在学术界、工业界、投资界引起了大量的关注,发展到现在已经将近一年半的时间。一年之前,就有一种说法,openai相比于开源社区的技术领先,大概在18个月左右(一年半的时间)。
至此,相比于ChatGPT(GPT-3.5)出圈,大概有一年半的时间,开源社区的引领者 Llama 发布了其3.1版本的模型,在各个榜单上面均超过了GPT-3.5,并且在个别榜单可以和GPT-4相互对比。从使用上来讲,Llama 3.1的使用体验,还是弱于GPT-4,但稳定能超过GPT-3.5。
开源社区这一年半来,在大模型领域做了大量的探索,总结了很多有价值的经验。Llama 3.1的技术报告使用的方法,可以认为是目前开源社区的集大成者。对LLama 3.1技术报告的解读,可以了解现在社区训练大模型最成熟、最先进的技术是什么样的,在实际训练模型的时候具有重要意义。
受众:
简要来说,LLama 3.1有以下独到之处:
后面将会从前到后讲解LLama 3.1的技术报告,并穿插对上述独到之处的讲解,在讲解的时候,会伴随着一些评论,这些评论会以背景色突出。
整体而言,Llama 3.1有如下模型特性:
整体而言,模型效果相比于同等级别的开源模型,有较大的领先;相比于GPT-4,在一些任务的指标上可以打平;相比于GPT-3.5,稳定领先。
由于预训练成本较高,几乎没有太多容错,要求尽可能一次性地能有好的结果。在大模型技术栈中,预训练是研究门槛最高、最需要工程师经验的环节。预训练模型的好坏,直接决定了后训练(Llama技术报告的说法,对应之前的alignment)的上限。
预训练主要有以下挑战:
针对上述挑战,Llama 3.1都提供了合理的解决方案,下面将会分别进行阐述。
数据的挑战是数据量和数据质量,数据量比较偏工程,需要优秀的工程师搭建出来数据处理的平台,进行数据的爬取、收集等。下面主要讲数据质量的处理,目前而言,数据质量处理主要包括安全过滤-质量过滤-去重三部分,安全过滤过滤掉隐私信息和不安全信息,防止模型在应用的时候输出此类信息;质量过滤是过滤掉低质量信息,更高质量的数据可以训练出更高质量的模型;去重是去除数据中重复的信息,正常的数据分布,具有一定的长尾性,长尾的数据会导致模型偏向于流行的数据分布,带来偏差,合理的去重对于模型整体的能力和长尾数据的表现都有利。
个人身份信息和安全性过滤:移除包含大量个人信息(例如姓名、电话、邮箱等)的数据、不安全的内容、成人内容等。这部分可以通过规则的策略,通过正则匹配来实现。
文本信息提取和清理:爬下来的数据,都是html格式的,文本信息隐含在html里面,为了提取出文本信息,需要用到html解析器,好的解析器能让文本的质量更高,Llama 3.1优化了解析器,得到了更好的数据质量。同时,对于code、数学公式等都保留原始格式,去除markdown的标记值,进一步提升整体的质量。
去重复:重复的信息,会降低训练效率,并且对于长尾信息不友好,因此去重成为了关键的数据处理流程。Llama 3.1采用了三种数据处理办法:
规则驱动的质量过滤:又称为启发式地质量过滤,主要是指的可以从文本中找一些特征,能够判别出数据质量较低,将这些数据过滤掉。例如,文本中有大量的乱码、特殊符号、不合理的文本长度等等,都可以作为质量过滤的特征。Llama 3.1的技术报告用到的规则有:
模型驱动的质量过滤:给出一些文档质量的标签,训练模型预测文本质量,基于训练后的模型进行过滤。常见的训练方法有:认为wikipedia的文本质量较高,其他质量较低,训练模型,这样的好处是无需人工标注;使用人工标注/模型标注的办法,给文档质量打分,训练模型。
上述操作中,文本提取和清理、去重复、规则驱动的质量过滤、模型驱动的质量过滤的复杂度都是O(n),均能处理海量的数据。前面四个均在CPU上可以实现,最后一个涉及到模型,需要用GPU实现,整体成本会更高;去重涉及到hash算法,相比于其他几个CPU的操作,计算成本更高。一般而言,我们可以在起始阶段采用计算成本更低的办法,以低的成本过滤数据,然后再用高成本的操作,以让整体的算力需求更低,执行更快。考虑到上述模块的计算成本,处理数据可以按照如下顺序:文本信息提取和清理->规则驱动的质量过滤->去重复->模型驱动的质量过滤,来保证数据处理的效率更高。
实际上,数据的领域分布是不均衡的:
针对领域不均衡的问题,需要设计合理的数据混合/上下采样比例,来达到最好的效果。由于在大模型上做数据混合比例的实验是不可能的,行之有效的策略是在小的数据集上做相关的实验,然后直接放到大数据集上面。这基于一个基本的假设:大小模型最优的数据混合比例是一致的,也是一种比较合理的假设和务实的做法吧。但是也可能会存在一些问题,一个可能的情况是,对于不同模型,数据混合的比例会有差异,且存在类似于scaling law的规律性,例如大的模型学习能力更强,需要更多难的数据。针对此猜想,可行的做法在小的不同规模的模型上做实验,看不同规模是否能总结出规律,如果可以,则能够泛化到大模型。
为了决定最好的采样和混合比例,Llama 3.1在小的模型上做了较多的实验,最终给出了一些建议值。Llama 3.1给出的建议配比是:50%英文通用数据、25%数学和推理数据、17%代码数据、8%多语言数据。需要注意的是,这个配比和评估相关,对于中文预训练,最优的配比会有所不同,需要重新实验。
与之前版本的LLama相同,3.1仍然采用dense模型,没有太多的变化。这里没有采用MoE的结构,听八卦是LLama团队的MoE没有训练好,如果八卦为真,反映了MoE的训练稳定性更差,且任何训练都有极高的门槛,强如Llama团队,在之前没有MoE积淀的情况下,也训练不好。如果传言为假,则需要思考思考为什么Llama没有选择MoE架构了,他们汇集了世界上最聪明的一批人,技术选型应该是明智的,MoE相比于Dense模型是否具有宣称的优势、又是否存在被忽略的短板,值得更进一步的思考和实验验证。
具体而言,LLama 3.1的一些小的设计包括:
Scaling Law 是个基于大量的实验总结出的经验规律,指导了过去大模型的迭代方向,主要是三点特性和应用:
实际上,模型训练的超参数(主要是学习率和batch size的设置)和scaling law也有一定关系。这部分可以参考 DeepSeek LLM Scaling Open-Source Language Models with Longtermism 这篇论文,展示了超参数和scaling law的关系,并给出了设置超参数的建议,对预训练具有很强的指导意义。
在Llama 3.1的技术报告中,对于405B的模型,采用了计算最优的做法,通过大量的小规模实验拟合曲线,推广到大模型规模,得出最优的模型和数据规模。具体而言,计算量在 6 × 10^{18} FLOPs 到 10^{22} FLOPs之间,模型规模在40M到16B之间,分别训练模型,统计loss。每个计算量可以有一个最优的模型规模和训练数据的组合,据此可以拟合曲线,然后得到在全量计算资源下,最优的模型规模和数据规模。对于Llama这次的集群规模而言,在合适的训练时间内,可以提供 3.8×10^25 FLOPs的计算量,按照之前拟合的曲线,计算最优的模型规模和数据量为402B和16.55T。实际上,用了405B和15T的数据。
硬件基础
这部分和算法没有太大关系,本文不计划讲的过于深入,感兴趣的读者可以参考Llama 3.1的技术报告原文。无论是对团队而言(有这么多显卡)还是对工程师而言(对硬件、算法都有深入理解),这套技术的搭建门槛极高,不适用于大多数团队和个人,大部分人了解即可。
并行化策略
在训练模型的时候,用到了4D并行化策略,组合了张量并行(TP)、流水线并行(PP)、上下文并行(CP)、数据并行(DP)的策略。4D并行也是目前做大规模模型预训练的标准配置,合理的4D并行策略,可以最大化利用GPU算力资源。举例而言,TP相比于PP对于通信需求更高,因此就更适合用在单机内部的显卡上面,最大化利用NVLink带来的优势。
实测下来,LLama 3.1的并行化策略,能够达到GPU计算峰值的40%,在16k的集群上能达到这种效果,非常了不起的。
目前预训练大多分为两个部分:
分成这两步,主要是出于训练效率的考虑,Transformer结构的计算复杂度随着模型长度平方增加,从头就采用长文本训练是昂贵的,在第一阶段,更加注重效率,用短文本训练;在第二阶段,更加注重长文本效果,用长文本训练。目前该设置已经成为大模型预训练的标准配置。
此外,LLama 3.1还引入了第三阶段的预训练:
3. 退火训练:使用高质量的数据,以小的学习率训练模型,使得模型能更好的在后处理阶段表现更好。
以下是一些具体的配置:
初始预训练
学习率:在405B的模型上,采用了 8 × 10^{−5} 的峰值学习率,8,000步的warmup,cosine学习率衰减,经过1,200,000训练步,衰减到 8 × 10^{−7} 。
Batch size:起始阶段,使用较小的batch size,然后增大batch size。具体而言,第一阶段,使用4k的序列长度,4M tokens的batch size,训练了252M tokens;第二阶段,使用8k的序列长度,8M token的batch size,训练了2.87T token;第三阶段,使用8k的序列长度,16M token的batch size,训练剩下的数据。这种预训练策略,能够比较稳定地训练模型。
数据混合:
LLama 3.1用了几个小tricks: - 增加非英语语言的数据比例,提升模型的多语言能力; - 上采样数学数据,提升推理能力; - 在最后阶段,增加更多时间更新的数据,提升模型的实效性; - 下采样质量较低的数据。
长上下文预训练
Llama 3.1在扩充长度的时候,采用渐进的方案:分6个阶段,逐渐将上下文从8k扩展到128k。在每次向更大的上下文扩充的时候,要保证两点:
这一阶段训练,使用了800B tokens。
退火训练
在最后的训练阶段,训练了40B tokens,学习率逐渐衰减到0,保持上下文长度128k。这部分选用低的学习率,并选取高质量的数据训练,保证模型在局部调整到更好的状态。训练完成后,将在退火阶段所有的模型checkpoint取平均,作为最终输出的预训练模型。这种操作的合理性是:退火阶段,学习率低,模型局部调整,因此取平均具有合理性,且实验验证效果更好。
后训练就是之前常说的对齐技术,包括SFT、DPO之类。除了人工标注数据之外,LLama 3.1大规模使用了以较低的成本生成的数据,在训练算法中的地位甚至超过了标注数据,这标志着合成数据训练模型已经逐渐成熟并会越来越重要,后面我会讲一下这背后的底层逻辑。
在现有的大模型主流认知里面,预训练解决的是模型知识的问题,其能决定模型的上限;后训练解决的是模型的对齐问题,其能让模型在预训练中获得的能力更好地发挥出来。后训练的效果,直接决定了模型的实际效果,对于资源消耗也更少。绝大多数团队,其实在训练模型的时候,是基于预训练模型做对齐的,因此,这部分内容是从业者应该着重关注的,包括训练的思路、合成数据的办法等。
整体做后训练的流程如图所示:
在拒绝采样的过程中,使用DPO模型生成多个数据。DPO模型作为最终的模型提供推理服务。
上述过程涉及到生成数据训练模型,越好的模型生成的数据越好、越容易训练出好的模型,因此上述训练过程,会迭代6次,在迭代的过程中优化模型、从而优化生成的数据、并提升生成数据训练得到模型的效果。此外,由于涉及到合成偏好数据,需要让模型有所差异,保证生成数据的差异性,因此在每个轮次,会使用不同的超参数、数据训练得到多个RM、SFT、DPO模型,最后会对于这些使用不同超参数、数据训练的的RM、SFT、DPO模型取平均,作为最终模型。
上述训练算法中,相比于SFT数据,偏好数据占据更加重要的部分,包括训练RM模型进行拒绝采样和训练DPO模型。LLama 3.1的偏好数据是由收集到的prompt通过模型生成多个回复结果,有人工标注回复的质量排序。这里的技术选型有很多内涵:
Reward Model的作用是能够判别模型生成内容质量的好坏,潜在的用途包括:强化学习中作为环境模拟提供反馈训练模型(PPO);在拒绝采样中,作为判别挑选数据训练模型;在模型评估中,作为质量评估的标准。
因为DPO训练更容易收敛,LLama 3.1采用了DPO的训练技术,训练Reward Model的主要作用是为提供拒绝采样提供判别,选择数据训练SFT模型。
训练Reward Model的具体方式:对于一个prompt,存在n个答案,答案质量有高低排序,排序作为标签可以训练模型。实际中,用pair-wise的数据(chosen, rejected),这些数据是模型合成两个response数据进行人工标注排序的。然后会把chosen给模型或人编辑得到更好的回复edited,最终得到了 edited > chosen > rejected,给模型训练。传统的Reward model训练,会把prompt和每一个答案计算出分数,共有n行数据,分别计算n个分数,设计loss训练模型。Llama 3.1的区别是,把prompt和多个答案打乱后拼接,一次性传播计算所有数据的分数,用来设计loss训练模型。这种训练方式更加高效,LLama 3.1做了消融实验,这种方案不会造成性能的损失。
SFT的数据包括借助于Reward model在人工的prompt上面通过拒绝采样生成的数据、人工标注的数据、高质量合成数据。在训练的时候,采用prompt mask的策略,只计算response的loss,不计算prompt的loss,根据目前多个的论文结果和我自己的实验结果,prompt mask相比于不mask 有微弱的优势。实际用1 * 10^{-5} 的学习率,训练了8.5k-9k步,这个实验设置比较稳定,能在各个数据混合下都有较好的表现。
DPO有两种:
Online DPO的好处是数据是用最新的模型生成的,因此得到的标签能够切合模型当前的训练情况(类似于active learning),使得样本的训练更加高效。
根据Llama 3.1的描述,采用了online DPO的训练策略,每次迭代后重新用最新的模型生成数据,进行标注,然后训练。训练的时候,用了 1 * 10^{-5} 的学习率,β 超参数设置为0.1,并且对DPO算法做了如下改进:
数据对于模型的优化至关重要。数据有两个方面,数据获取、数据质量过滤。下面首先将偏好数据如何获得,偏好数据用来Reward model和DPO模型;然后将SFT数据如何获得,SFT数据用来训练SFT模型;最后讲数据处理和数据质量过滤方法。
在LLama 3.1的报告中,偏好数据是用模型生成,然后人工标注的。用不同的超参数和数据训练出不同的模型,保证模型和模型生成数据的多样性。整个过程的输入是收集到的prompt,,每次从中选取两个模型对收集到的prompt生成答案,然后人工标注优劣。除了标注优劣顺序外(chosen > rejected),还会给出优势的大小,分成四个层级:明显更好、更好、轻微好、差不多。然后针对chosen进行人工或模型编辑,得到edited,最终得到edited > chosen > rejected的数据。
数据类型包括:通用英语、知识问答、指令跟随(上述三者约80%)、代码、多语言、推理、工具使用(后面四者约20%)。知识问答和指令跟随,是为了让回答更加准确,符合人的预期。数据是多轮交互数据,有相对较长的问题和回复,来增加问题的难度。
由于训练涉及到多个轮次,每个轮次都会用最新的模型重新进行数据的生成和标注。对于DPO模型的训练,只用最新轮次的标注数据训练模型;对于Reward模型,用所有的标注数据训练模型。直观来讲(有点强行解释,我没太看懂这个设计),这样做原因是DPO模型作用是后续提供服务,是一个迭代的过程优化的,越新的数据对于当前模型状态,向alignment的方向优化越有意义;而Reward模型是用来判别数据质量,对Alignment并不敏感,所以用更多的数据,有利于其学习到判别质量的能力。
SFT的数据来自于三部分:
最终的数据中,混合了约50%通用英文数据、15%代码数据、3%多语言数据、8%考试数据、21%推理和工具数据、0.11%长文本数据。
数据处理和质量过滤
由于数据是生成的,其质量过滤较为重要。质量过滤用到了规则驱动的、模型驱动的两种。
规则驱动:主要是由人来看数据,总结一些模式。例如发现早期的训练中,包含较多的emoji数据或者exclamation数据(例如倾向于I'm sorry xxx; I apologize xxx)。
模型驱动:基于模型做出判别,包含:
实际上,会首先基于RoBERTa的embedding聚类,在类内根据质量*难度进行打分排序,从上到下进行数据挑选,在挑选的时候,只保留和前面数据的相似度较低的数据,保证数据的多样性。
Llama 3.1关注的几个模型特性包括:代码、多语言、数学和推理、长上下文、工具使用、事实推断、可控制性等。每一种特性都有其特殊的挑战,Llama 3.1都有会结合这个领域的特点对应的算法设计,实现层面,一个很重要的点就是要有领域专家的参与,基于领域的特点设计出做数据的规则,越优秀的专家设计出的规则越好,对于训练越有利,在设计规则的时候有两点是值得考虑的:这个领域的特点和难点是什么;规则能够为模型带来什么。下面主要讲一下代码的处理办法。
代码领域的难点是:相比自然语言,代码需要较高的专业背景才可以看懂,让人工标注需要大量的成本;潜在的优势是:代码是可以被分析和执行的。因此,利用这些规则,对合成数据进行质量过滤,保留质量较高的数据训练模型,是合理的方法。Llama 3采用了大量合成数据策略,来生成SFT数据训练代码模型。
由于代码是比较大的细分领域,训练了专门的代码专家模型来支持代码的后训练过程。在实际处理的时候,主要注重代码生成、写文档、debug、和评审的能力。
代码专家:由于代码领域和通用数据有较大的差异,且代码本身的数据量也足以支持与训练,这里继续预训练代码专家模型来进行优化——在代码数据占比85%的数据上,进行了1T tokens;最后1k步,用16k上下文,做项目级别的训练。然后在这个模型基础上,用代码数据做代码后训练,得到最终的代码专家模型。这个代码专家模型的作用主要是合成数据,给主模型训练,包括给主模型训练相关的代码prompt做拒绝采样,最终代码专家的代码能力,也会融入到主模型里面。
合成数据生成:借助于代码专家模型和LLama 3.1主模型,进行数据合成,合成的数据用于主模型的后训练,提升主模型的代码能力。这里共合成了2.7M条数据,由于是合成数据,数据量很大。包含以下处理思路:
拒绝采样的prompt引导:在做拒绝采样的时候,有更加精细的prompt操控,即在prompt中引导从代码可读性、文档化、周密性、具体性的角度做样本选择。
使用模型判别信号的数据过滤:在拒绝采样中,由于两点原因:prompt来自于收集的prompt,由其产生的数据是要高于模型生成的prompt的,要尽可能好好利用;用户在使用LLM的时候,也并不一直期望代码的正确性,例如生成伪代码、甚至错误的代码也能够拷贝,稍作修改就可以用。因此,拒绝采样中并没用选用静态分析/动态分析的方法过滤数据,而是使用LLama 3做判别来过滤数据。具体而言,让Llama 3判断代码争取性和代码风格的好坏,只有正确且风格好的代码才会被留下来训练模型。然而,这个方法会让困难的数据被筛选掉,导致模型效果降低,为了解决这个问题,反复让模型修改难样本,直至达到上述要求。
大模型发展至今,已经过去一年多的时间了。站在现在的时间节点看,尽管国内大模型、开源社区相比于 openai 仍然有较大的差距,但是取得国内技术和开源社区的成绩已经远超去年 openai 刚开始发布模型时候大家的期望。开源极大地促进了大模型的发展,一方面是优秀、有价值的经验得到交流,避免不同团队走相同的弯路,导致社会资源的浪费;另一方面,从事开源事业的人因为会把自己花费心血得到的结论告诉世界,也会有更强的愿景,以更加负责任的心态把事情做好。LLama 3/3.1的发布标志着开源社区已经能够训练出质量极高的模型,而且其训练细节也透明可复制。可以预见的是,随着硬件的进一步优化,训练成本会进一步降低,未来开源社区的力量也会越来越强。
相比于调用API,开源模型从本身可以私有化微调、部署,具备更加安全、可控的特性,在一些特别定制化、数据安全要求高的场景上有一定的优势,这些场景会推进开源模型的进一步应用和繁荣。同时,像 openai 的闭源模型,已经收集到了大量的用户prompt优化模型,这是openai的先发优势,这是openai这种中心化的闭源模型带来的优势。对于开源模型,用户数据对于优化模型的收益仍然很高,LLama 3.1设计了合理的算法利用这些数据,开源模型未来的应用会更加偏向于一种去中心化的私有化场景,对于这些场景,如何收集数据,会是一个有价值的议题的思考方向。
本解读覆盖的内容:把LLama 3.1技术报告的精华部分(LLM的预训练和后训练)都讲的比较透彻了,当然还有一些章节没有讲,比如后训练的其他能力数据合成办法、评估、推理、多模态相关的内容,这些内容其实也有很多可以借鉴学习的,以后可以继续分享。
原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。
如有侵权,请联系 cloudcommunity@tencent.com 删除。
原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。
如有侵权,请联系 cloudcommunity@tencent.com 删除。