评估与测试

164 阅读53分钟

正如我们在本书中所讨论的,LLM代理和系统在各个行业中有着广泛的应用。然而,将这些复杂的神经网络系统从研究阶段推向现实世界的部署,面临着重大挑战,这就需要健全的评估策略和测试方法。

在LangChain中评估LLM代理和应用,采用了新的方法和指标,有助于确保系统的优化、可靠以及符合伦理要求。本章将深入探讨评估LLM代理的细节,涵盖系统级评估、以评估驱动设计、离线和在线评估方法,以及带有Python代码的实际示例。

通过本章学习,您将全面了解如何评估LLM代理,并确保它们与预期目标及治理要求保持一致。总体而言,本章内容包括:

  • 评估为何重要
  • 我们评估什么:核心代理能力
  • 如何评估:方法论和途径
  • LLM代理的实际评估

离线评估

本章的代码可在本书GitHub仓库的chapter8/目录中找到。鉴于该领域的快速发展及LangChain库的更新,我们承诺保持GitHub仓库的及时更新。请访问 github.com/benman1/gen… 获取最新内容。

有关环境搭建说明,请参见第二章。如果您在运行代码时有任何疑问或遇到问题,请在GitHub上创建issue,或加入Discord讨论群:packt.link/lang

在开发LLM代理的过程中,评估起着关键作用,确保这些复杂系统在真实应用中稳定、高效地运行。让我们从为什么必须进行严谨评估开始讨论吧!

为何评估至关重要

LLM代理代表了一类新型的人工智能系统,结合了语言模型、推理、决策和工具使用能力。与传统行为可预测的软件不同,这些代理具备更高的自主性和复杂性,因此在部署前进行全面评估至关重要。

考虑现实世界的后果:与确定性行为的传统软件不同,LLM代理会做出复杂且依赖上下文的决策。如果在实施前未经过评估,客服领域的AI代理可能会提供误导信息,损害品牌声誉;医疗助手可能会影响关键治疗决策——这正体现了彻底评估的重要性。

在深入具体评估技术之前,需区分两种根本不同的评估类型:

  1. LLM模型评估:
  • 聚焦于基础语言模型的原始能力
  • 采用受控提示和标准化基准测试
  • 评估固有能力,如推理、知识回忆和语言生成
  • 通常由模型开发者或研究人员进行,比较不同模型表现
  1. LLM系统/应用评估:
  • 评估包含LLM及其附加组件的完整应用
  • 检验实际用户查询和场景下的现实表现
  • 评估各组件(检索、工具、记忆等)的协作效果
  • 测量端到端解决用户问题的有效性

两者均重要,但本章重点是系统级评估,因为使用LangChain构建LLM代理的从业者更关注整体应用性能,而非基础模型的对比。一个基础模型较弱但提示工程和系统设计出色的应用,可能在真实场景中表现优于基础模型强但整合差的应用。

安全性与对齐

LLM中的“对齐”具有双重含义:作为过程,是指训练后采用的技术以确保模型行为符合人类期望和价值观;作为结果,是衡量模型行为符合预期人类价值和安全规范的程度。与关注准确性和完整性的任务相关性能不同,对齐关注系统与人类行为标准的根本校准。微调提升模型在特定任务上的表现,而对齐专注于伦理行为、安全性及减少有害输出。

这一区别非常关键:模型可能能力强大(微调良好),但对齐差,生成的内容复杂却违反伦理或安全准则;反之,模型对齐良好但在某些领域缺乏特定任务能力。与人类价值观的对齐是负责任AI部署的基础。评估必须验证代理在多个维度上与人类期望对齐:敏感领域的事实准确性、伦理界限识别、安全响应以及价值一致性。

对齐评估方法必须针对领域特定问题定制。在金融服务领域,对齐评估关注GDPR和欧盟AI法案等法规合规,尤其是自动化决策。金融机构需评估欺诈检测系统中的偏见,实施适当的人类监督机制,并记录流程以满足监管要求。零售环境中,对齐评估聚焦伦理个性化实践,平衡推荐相关性与客户隐私关注,确保生成个性化内容时数据使用的透明性。

制造领域的对齐评估着重安全参数和操作边界。AI系统必须识别潜在危险操作,维持质量控制的人类干预协议,并遵守行业安全标准。对齐评估包括测试预测性维护系统是否适当将关键安全问题上报给人工技术人员,而非自动决定安全关键设备的维护计划。

教育领域的对齐评估需考虑不同学生年龄组的发展适宜性、公平评估标准以及适当的透明度。教育AI系统需评估其提供复杂话题平衡视角的能力,避免在学习示例中强化刻板印象,并在敏感或细微问题上适时向人类教育者让步。这些领域特定的对齐评估对于确保AI系统不仅在技术上表现良好,更在伦理和安全边界内运行,适应其应用环境至关重要。

性能与效率

正如早期软件测试面临的挑战通过标准化实践得到解决一样,代理评估也面临类似难题,包括:

  • 过拟合:系统仅在测试数据上表现良好,但在真实环境中表现欠佳
  • 针对基准测试“作弊”:优化特定测试场景而非通用性能
  • 评估数据集多样性不足:未覆盖系统将在现实环境中遇到的各类情况,包括边缘案例和异常输入

借鉴软件测试及其他领域的经验,全面的评估框架需要不仅衡量准确性,还要评估LLM代理的可扩展性、资源利用率和安全性。

性能评估旨在确定代理能否可靠地实现预期目标,涵盖:

  • 在多样场景中的任务完成准确性
  • 处理与评估样本不同的新颖输入的鲁棒性
  • 抵抗对抗性输入或操控的能力
  • 计算与运营成本的资源效率

严格的评估能识别多种真实场景下潜在的失败模式和风险,正如现代基准测试和竞赛所展示的。确保代理能在各种现实条件下安全且可靠地运行至关重要。评估策略和方法不断演进,通过迭代改进提升代理设计的有效性。

有效的评估通过在准确性与资源效率之间取得平衡,防止采用不必要的复杂且昂贵的方案。例如,DSPy框架在优化成本和任务性能方面表现出色,说明评估如何引导资源高效的解决方案。LLM代理也受益于类似的优化策略,确保其计算需求与效益相符。

用户与利益相关者价值

评估有助于量化LLM代理在实际环境中的真实影响。新冠疫情期间,WHO部署的筛查聊天机器人展示了AI如何通过用户遵守度和信息质量等指标实现实际效果。金融服务领域,摩根大通的COIN(合同智能)平台通过减少36万小时的人工审核工作体现价值,评估关注准确率和成本节约。类似地,丝芙兰的美容机器人通过提升6%的转化率和更高的平均订单价值,证明了其多维度的利益相关者价值。

用户体验是成功AI部署的基石。Alexa和Siri等系统经过严格的易用性和互动性评估,指导设计改进。同样,评估用户与LLM代理的交互有助于优化界面,确保代理满足或超越用户预期,从而提升满意度和采用率。

现代AI系统的一个关键方面是理解人类干预对结果的影响。在医疗场景中,评估显示人类反馈提升了治疗型聊天机器人的表现。在制造业,一家大型汽车制造商部署的预测维护LLM代理通过减少停机时间(提升22%)、延长设备寿命以及维护技师对系统可解释性和实用性的积极反馈体现了价值。对LLM代理而言,将人类监督纳入评估能揭示决策过程的洞察,突出优势与改进空间。

全面的代理评估需兼顾生命周期内多方利益相关者的不同视角和优先级。评估方法应反映这种多样性,并根据各方主要关注点量身定制指标。

  • 终端用户主要从任务完成和交互质量角度评估代理,关注代理准确理解并执行请求(任务成功率)、提供相关答案(回答相关性)、维持对话连贯性及响应速度(响应时间)。他们尤为重视满意度指标,尤其在对话场景中用户满意度和沟通效率。特定应用领域如网页导航或软件开发,用户可能更侧重于领域特定的成功指标,比如电商代理是否成功完成购买,编码代理是否正确解决软件问题。
  • 技术利益相关者关注代理的内部过程质量而非仅仅结果,聚焦规划质量(计划可行性和最优性)、推理连贯性、工具选择准确性及技术约束遵守。软件工程代理特别关注代码正确性和测试用例通过率。技术团队还密切监控计算效率指标,如Token消耗、延迟和资源利用,这些直接影响运营成本和扩展性。评估还包括代理的鲁棒性,测量其如何处理边缘案例、从错误中恢复及在不同负载下的表现。
  • 业务利益相关者通过与组织价值直接相关的指标评估代理。除基本ROI计算外,他们关注领域特定KPI,如客服代理减少的呼叫量、零售应用提升的库存准确率、制造代理降低的停机时间。评估框架涵盖代理与战略目标的契合度、竞争力差异化以及组织内的可扩展性。在金融领域,连接技术表现与业务成果的指标尤为重要,如在保障客户便利的同时减少欺诈损失。
  • 监管利益相关者,尤其在医疗、金融和法律等高风险领域,通过严格的合规和安全标准评估代理。评估包括代理对领域特定法规(如医疗领域的HIPAA或银行金融监管)的遵守情况,偏见检测措施,对抗性输入的抵抗力,以及决策过程的全面文档化。对于这类利益相关者,安全测试的彻底性及代理在设定范围内的稳定表现比纯粹的效率或能力指标更重要。随着自治代理的广泛部署,监管评估维度变得愈发关键,以确保伦理运作并最大限度减少潜在伤害。
  • 组织决策者在部署阶段特别关注成本效益分析。医疗领域评估AI介入与传统方法的成本效益以确保经济可行性。同样,评估LLM代理部署的财务可持续性需要分析运营成本与取得的效率,确保在不牺牲效能的前提下实现可扩展性。

为LLM评估建立共识

由于LLM代理的开放性和“良好表现”这一概念的主观性、依赖上下文的特点,评估LLM代理面临重大挑战。与具有明确度量标准的传统软件不同,LLM可能会“看似合理地出错”,且人们对其质量的判断存在差异,因此需要一种以建立组织共识为核心的评估策略。

有效评估的基础在于优先关注用户结果。开发者应从用户视角出发,明确成功的定义,理解代理应实现的价值及潜在风险,而非单纯从技术指标开始。基于结果的方法确保评估重点与现实影响保持一致。

针对LLM评估的主观性,必须建立健全的评估治理机制。这包括组建由技术专家、领域专家及用户代表组成的跨职能工作组,共同制定并记录正式的评估标准。明确不同评估维度的责任归属以及争议解决的决策机制至关重要。对评估标准进行版本控制,确保随着理解的深化保持透明。

在组织环境中,平衡多方利益相关者的视角是关键。评估框架必须兼顾技术性能指标、领域特定的准确性及以用户为中心的实用性。有效的治理通过加权评分系统和定期跨职能审查促进这种平衡,确保各方观点得到充分考虑。

最终,评估治理作为组织学习的机制,结构化的框架有助于识别具体的失败模式,提供可执行的改进建议,实现系统版本间的量化比较,并通过反馈循环支持持续优化。成立涵盖所有利益相关方代表的“模型治理委员会”有助于审查评估结果、调解分歧并指导部署决策。除了结果外,记录围绕评估的讨论也能捕捉用户需求和系统局限的宝贵洞见。

总之,严谨且治理完善的评估是LLM代理开发生命周期的重要组成部分。通过实施兼顾技术性能、用户价值和组织协调的结构化框架,团队能确保系统高效交付价值,同时有效规避风险。接下来的章节将深入探讨评估方法论,并提供适用于使用LangChain等工具的开发者的具体案例。

在建立了LLM代理评估的基本原则及治理重要性的基础上,我们现在转向评估的实际操作。开发可靠的代理需要明确哪些行为方面需被测量,以及如何运用有效的技术对其性能进行量化。后续章节将详细指导评估LLM代理的“评什么”和“怎么评”,解析应重点关注的核心能力,并介绍多样化方法,助你构建全面的评估框架。

我们评估的内容:核心代理能力

从最根本的层面来看,LLM代理的价值直接取决于其成功完成设计任务的能力。如果代理无法可靠地完成其核心功能,那么无论其底层模型或工具多么先进,其实用性都会大打折扣。因此,任务绩效评估构成了代理评估的基石。下一小节中,我们将探讨如何衡量任务成功的细节,重点考虑在实际场景中评估代理执行核心功能的有效性。

任务绩效评估

任务绩效是代理评估的基础,衡量代理实现既定目标的有效程度。成功的代理不仅完成任务率高,而且产出的响应相关且事实准确,直接满足用户需求。在评估任务绩效时,组织通常会同时考察最终输出的正确性和实现过程的效率。

TaskBench(Shen等,2023)和AgentBench(Liu等,2023)提供了针对基于LLM代理的多阶段标准化评估。TaskBench将任务分解为任务分解、工具选择和参数预测三个阶段,报告显示像GPT-4这类模型在单工具调用上的成功率超过80%,但端到端任务自动化成功率下降到约50%。AgentBench的八个交互环境同样显示,顶级专有模型远超小型开源模型,凸显跨领域泛化的挑战。

金融服务领域的实际应用展示了任务绩效评估,尽管行业报告的指标需谨慎看待。许多机构声称文档分析系统准确率高,但独立学术评估发现其在现实环境下性能明显下降。受监管行业特别重视代理识别自身信息不足的能力——这是一项关键安全特性,需采用超越简单准确率的专项评估协议。

工具使用评估

工具使用能力,即代理选择、配置并利用外部系统的能力,是区分高级代理和简单问答系统的重要评估维度。有效的工具使用评估涵盖多个方面:代理是否能为特定子任务选对工具,是否提供正确参数,能否正确解释工具输出,并将其整合成连贯的解决方案。

Liu等(2023)开发的T-Eval框架将工具使用拆解为多个可测能力:规划调用顺序、推理下一步、检索正确工具、理解工具文档、正确格式化API调用、以及审查响应以判定目标达成。此细化方法帮助组织发现代理在工具使用中的具体薄弱环节,而非仅关注整体失败。

最新基准如ToolBench和ToolSandbox显示,即便是顶级代理,在动态环境中使用工具仍有困难。生产系统的评估逐渐注重效率指标,除了基本正确性,还测量代理是否避免冗余工具调用、减少不必要API使用,并选择解决问题的最直接路径。尽管行业实现宣称效率大幅提升,同行评议研究显示实际增益更为温和,优化工具选择在受控研究中通常能降低15%-20%的计算成本,同时保持结果质量。

RAG评估

RAG系统评估是代理评估中的专业但关键领域,聚焦于代理检索和整合外部知识的有效性。完整的RAG评估基于四个关键维度:检索质量、上下文相关性、忠实生成和信息综合。

  • 检索质量 衡量系统从知识库中找到最合适信息的能力。现代评估不单看相关度分数,还通过不同排名的精确率和召回率评估,考量检索文档的绝对相关性及对回答需求信息的覆盖度。学术界开发了带有专家注释的标准化测试集,便于系统比较不同检索方法。
  • 上下文相关性 评估检索信息与查询表达的具体信息需求的匹配度,考察系统能否区分表面相似但上下文不同的请求。近期研究为金融领域开发了专门的消歧评估方法,针对术语相近但产品或法规根本不同的查询,衡量检索系统区分此类查询的能力。
  • 忠实生成 指代理响应在多大程度上准确反映检索信息,避免虚构细节,是RAG评估中最关键的方面之一。研究发现,即使是优化良好的RAG系统,在复杂领域中虚假率仍达3%-15%,凸显挑战。研究者开发了多种忠实度评估协议,如源归属测试和矛盾检测机制,系统比对生成内容与原始来源。
  • 信息综合质量 评估代理整合多源信息形成连贯、结构良好响应的能力。高级代理不仅仅是简单拼接或复述单个文档,而是需要调和潜在冲突信息,呈现平衡观点,合理组织内容。此评估超越自动指标,需专家评估代理在保留适当细节的前提下,如何将复杂信息综合成易懂准确的总结。

规划与推理评估

规划与推理能力构成了代理解决复杂多步骤问题的认知基础,这类问题无法通过单一操作完成。评估这些能力需要超越简单的输入-输出测试,关注代理的思维过程和问题解决策略的质量。

计划可行性 衡量拟议计划中每一步行动是否符合领域的前提条件和约束。Valmeekam等人在2023年发表的论文《PlanBench: An Extensible Benchmark for Evaluating Large Language Models on Planning and Reasoning about Change》中,使用PlanBench评测套件发现,GPT-4在零样本条件下仅能在约34%的经典IPC风格领域生成完全可执行的计划——远低于可靠阈值,凸显了模型在考虑环境动态和逻辑前提方面的持续失败。

计划最优性 除了基本可行性,还关注效率。该维度评估代理是否能够识别不仅是任何可行方案,而是实现目标的最高效路径。Recipe2Plan基准专门测试代理在时间限制下的多任务处理能力,反映现实世界对效率的需求。目前最先进模型仍有显著提升空间,公开研究显示即使是最优秀系统,最优计划生成率也仅在45%-55%之间。

推理连贯性 评估代理解决问题的逻辑结构——包括单个推理步骤之间的逻辑连接、结论是否合理由前提推导而来、以及在复杂分析中是否保持一致性。与传统软件测试只关注最终输出不同,代理评估越来越多地关注中间推理步骤,以发现那些最终答案正确但逻辑过程存在缺陷的问题。多项学术研究强调了该方法的重要性,多个研究团队开发了标准化的推理轨迹分析方法。

近期研究(如2023年《CoLadder: Supporting Programmers with Hierarchical Code Generation in Multi-Level Abstraction》与2024年《Generating a Low-code Complete Workflow via Task Decomposition and RAG》)表明,将代码生成任务分解为更小且明确的子任务(常采用层次化或按需规划),在基准测试和实际工程环境中显著提升了代码质量、开发效率和系统可靠性。

在明确了LLM代理评估的基础原则和建立稳健治理机制的重要性后,我们转向评估的实际操作层面。开发可靠的代理需要清晰了解其行为中需要测量的关键方面,以及如何应用有效技术对其性能进行量化。

确定核心评估能力是第一关键步骤。下一步是考虑如何有效测量这些能力,鉴于LLM代理相比传统软件的复杂性和主观性,单一指标或方法显然不足。下一小节将探讨多种评估方法与途径,帮助构建稳健、可扩展且具洞察力的代理性能评估体系。内容涵盖自动化指标在一致性评估中的作用、人类反馈在主观评价中的必要性、系统级分析对集成代理的重要性,以及如何将这些技术结合,形成促进持续改进的实用评估框架。

评估方法与途径

LLM代理,尤其是那些使用LangChain或LangGraph等灵活框架构建的,通常由不同的功能模块或技能组成。代理的整体表现不是单一的统一指标,而是这些单项能力执行的好坏及其协同效率的结果。在接下来的章节中,我们将深入探讨区分高效代理的核心能力,明确应评估的具体维度,以了解代理在哪些方面表现优异,哪些方面存在不足。

自动化评估方法

自动化评估方法提供了可扩展且一致的能力测评,支持不同版本或实现间的系统比较。虽然没有单一指标能全面反映代理性能,但通过结合多种互补手段,可以实现全面的自动化评估,辅助人工评审。

基于参考答案的评估将代理输出与一个或多个黄金标准答案或路径进行对比。早期的BLEU/ROUGE指标和嵌入相似度(如BERTScore、Universal Sentence Encoder)是重要的基础,但现今先进的评估依赖学习型指标(如BLEURT、COMET、BARTScore)、基于问答的框架(QuestEval)和由LLM驱动的“裁判”系统,这些均依托大规模人工标注数据,确保评估具有语义理解能力和鲁棒性。

现代评估越来越多采用基于准则的评价框架,针对特定需求对输出结果进行考核。例如,T-Eval框架将工具使用拆解为多阶段流程,考察规划、推理、工具选择、参数构造及结果解释。此结构化方法能精准定位代理失败环节,提供远比简单成败指标更具操作价值的洞见。

“LLM作为裁判”是快速发展的评估方法,利用强大语言模型作为自动评审员,依据定义好的评分标准对结果进行评价。Zheng等人(2023年,《Judging LLM-as-a-Judge with MT-Bench and Chatbot Arena》)的研究表明,经过精心设计的提示,GPT-4等模型能在人类评审者关注的事实准确性、连贯性和相关性方面达到高度一致。该方法有助于评估传统指标难以捕捉的主观质量,但研究者也强调需有人类复核以防评审模型自身的偏见。

人类参与的评估

人工评估对于测量自动化指标无法全面覆盖的主观维度依然不可或缺。有效的人类参与评估需要结构化的方法,确保评估一致性、减少偏差,同时发挥人工判断的最大价值。

专家评审提供领域专家的深入定性分析,能识别细微错误、评估推理质量及与领域最佳实践的契合度。现代专家评审采用标准化量表,将评估细化为多个具体维度,常用李克特量表或比较排序。医疗和金融领域的研究已制定出标准化专家评估协议,特别针对复杂监管环境中代理响应的评估。

用户反馈收集终端用户在实际交互中的体验。通过内嵌评分机制(如点赞/点踩、1-5星评级)获取量化数据,辅以文本评论提供定性洞见。对话代理效果的学术研究越来越多采用系统化的反馈收集,分析用户评分以识别不同查询类型、用户群体或时间段内的表现模式。

A/B测试通过随机将用户分流至不同版本或配置,控制比较代理差异,评估提示、工具集成或检索机制改动的效果。通常定义主要指标(如任务完成率、用户满意度)和次要指标(如回答长度、工具调用频率、对话时长),辅助解释性能变化。对话代理优化的研究证明,受控实验对发现配置改进尤为有效。

系统级评估

系统级评估对复杂LLM代理(特别是RAG系统)至关重要,仅测试单个组件不足以覆盖整体表现。研究表明,大量失败(某些研究中超60%)源于组件间集成问题,单独功能正常但整体协同出错。例如,检索文档未正确使用、查询改写改变原意、上下文窗口截断信息等。系统级评估通过追踪信息流和整体性能来定位此类问题。

核心方法包括利用诊断框架跟踪信息流(如RAG诊断工具),以及观察性工具(如LangSmith、Langfuse、DeepEval)以可视化推理链并定位错误。端到端测试采用全面场景评估系统处理模糊输入、挑战性请求及多轮上下文维护能力,代表框架如GAIA。

评估实施建议

  • 定义业务指标:识别对组织关键的功能性指标(准确率、完整性)、技术指标(延迟、令牌消耗)及用户体验指标(有用性、清晰度),为每个应用设定明确的测量标准。
  • 构建多样化测试集:开发涵盖常见查询、边缘案例及合规风险的全面测试集,系统分类保证广泛覆盖,持续扩充以反映新使用模式和失败案例。
  • 结合多种评估方法:将事实准确性和正确性的自动检查与领域特定标准相结合,结合定量指标和专家定性评估,确保全面性。
  • 分阶段部署:从离线基准测试开始,逐步向有限用户群发布,仅在满足性能阈值后全面推广,提前发现并修复问题。
  • 生产环境监控:实时跟踪关键指标(响应时间、错误率、令牌使用、用户反馈),设立异常告警防止性能下降。
  • 建立改进循环:将评估结果转化为具体改进方案,根因分析,实施解决措施,通过再评估验证效果,记录问题模式和成功经验。
  • 促进跨职能协作:纳入技术团队、领域专家、业务和合规人员多方观点,定期开展跨部门评审,确保全面评估。
  • 维护动态文档:集中记录评估结果、改进措施和成效,构建组织知识库,促进经验积累和迭代优化。

现在,让我们从理论走向实践,深入探讨如何评估LLM代理吧!

评估LLM代理的实际应用

LangChain提供了多种预定义评估器,用于不同的评估标准。这些评估器可以基于特定的评分标准或准则集来评估输出结果。一些常见的评估标准包括简洁性、相关性、正确性、连贯性、有帮助程度以及争议性。

我们还可以使用不同的方法,将LLM或代理的结果与参考结果进行比较,从成对字符串比较、字符串距离到嵌入向量距离。评估结果可用于根据输出对比来确定首选的LLM或代理。还可以计算置信区间和p值,以评估评估结果的可靠性。

接下来,我们先了解一些基础内容,并应用实用的评估策略。以LangChain为例。

结果正确性评估

举个例子,验证LLM回答是否正确(或者偏差多少)。比如询问“联邦储备当前利率是多少?”时,可以用精确匹配和字符串距离评估器来对比输出与参考答案:

from langchain.evaluation import load_evaluator, ExactMatchStringEvaluator

prompt = "What is the current Federal Reserve interest rate?"
reference_answer = "0.25%"  # 假设这是正确答案

# LLM的示例预测:
prediction_correct = "0.25%"
prediction_incorrect = "0.50%"

# 初始化忽略大小写的精确匹配评估器
exact_evaluator = ExactMatchStringEvaluator(ignore_case=True)

# 评估正确预测
exact_result_correct = exact_evaluator.evaluate_strings(
    prediction=prediction_correct, reference=reference_answer
)
print("Exact match result (correct answer):", exact_result_correct)
# 期望输出:分数为1(或'Y'),表示完全匹配

# 评估错误预测
exact_result_incorrect = exact_evaluator.evaluate_strings(
    prediction=prediction_incorrect, reference=reference_answer
)
print("Exact match result (incorrect answer):", exact_result_incorrect)
# 期望输出:分数为0(或'N'),表示不匹配

显然,如果输出格式不同或者想衡量偏差程度,这种方法就不太适用。仓库里有个自定义比较实现,可以解析像“It is 0.50%”和“A quarter percent”这类回答。

更通用的方法是使用“LLM作为裁判”评估正确性。在此示例中,我们不使用简单字符串匹配,而是调用一个评估用的LLM(如Mistral这类中高端模型),它会解析并评分提示、预测与参考答案,输出数值分数和推理说明。这种方法适合预测措辞不同但含义正确的情况。

from langchain_mistralai import ChatMistralAI
from langchain.evaluation.scoring import ScoreStringEvalChain

# 初始化评估用LLM
llm = ChatMistralAI(
    model="mistral-large-latest",
    temperature=0,
    max_retries=2
)

# 创建评分链
chain = ScoreStringEvalChain.from_llm(llm=llm)

# 定义输入、预测和参考答案
finance_input = "What is the current Federal Reserve interest rate?"
finance_prediction = "The current interest rate is 0.25%."
finance_reference = "The Federal Reserve's current interest rate is 0.25%."

# 使用评分链评估预测
result_finance = chain.evaluate_strings(
    input=finance_input,
    prediction=finance_prediction,
)

print("Finance Evaluation Result:")
print(result_finance)

输出示例显示LLM评估器如何进行细致推理:

Finance Evaluation Result:
{'reasoning': "助手的回答缺乏时间或信息来源说明。联邦储备利率会随时间变化,不是固定值。缺少具体时间或来源,该信息可能不准确。应建议用户查询联邦储备官网或权威财经资讯。回答缺乏深度和准确性。评分:[[3]]",
 'score': 3}

此评估突出“LLM作为裁判”方法的优势:能发现简单匹配忽略的细节问题。在该例中,评估器正确指出回答缺少关键上下文。3分(满分5)相比二元对错更细致,为开发者改进金融应用中的响应质量提供了可行反馈。

下一个示例演示如何用Mistral AI在有参考答案时评估模型预测。请确保设置了MISTRAL_API_KEY环境变量,并安装所需包:pip install langchain_mistralai。若按第2章安装流程,应该已安装。

这种方法适合有标准答案的事实性问题,评估预测与预期匹配程度。

from langchain_mistralai import ChatMistralAI
from langchain.evaluation.scoring import LabeledScoreStringEvalChain

llm = ChatMistralAI(
    model="mistral-large-latest",
    temperature=0,
    max_retries=2
)

labeled_chain = LabeledScoreStringEvalChain.from_llm(llm=llm)

finance_input = "What is the current Federal Reserve interest rate?"
finance_prediction = "The current interest rate is 0.25%."
finance_reference = "The Federal Reserve's current interest rate is 0.25%."

labeled_result = labeled_chain.evaluate_strings(
    input=finance_input,
    prediction=finance_prediction,
    reference=finance_reference,
)

print("Finance Evaluation Result (with reference):")
print(labeled_result)

输出示例:

{'reasoning': "助手回答有帮助、相关且正确。直接回应了用户关于联邦储备利率的问题,但未提供利率如何决定或对经济影响等额外信息。评分:[[8]]",
 'score': 8}

注意评分从之前的3分大幅提升到8分,显示了参考答案在评估中的重要性。无参考时评估着眼于缺少引用和时间戳,有参考时则侧重回答完整性和深度。

这两种方法均利用Mistral LLM作为评审员,提供比简单字符串匹配或统计方法更细致、上下文感知的评估。使用temperature=0时结果应保持一致,尽管模型版本和服务端变化可能导致输出略有不同。

由于模型版本和LLM响应的固有多样性(与temperature设置相关),您的结果可能与书中示例有所差异。

评估语气与简洁性

除了事实准确性之外,许多应用还要求回复满足一定的风格标准。例如,医疗健康应用必须以友好、平易近人的语气提供准确的信息,同时避免用不必要的细节让患者感到困扰。下面的示例演示了如何利用LangChain的标准评估器来评估简洁性和语气,帮助开发者衡量这些主观但关键的回复质量方面:

首先,我们导入评估器加载器和用于评估的聊天型LLM(例如GPT-4o):

from langchain.evaluation import load_evaluator
from langchain.chat_models import ChatOpenAI

evaluation_llm = ChatOpenAI(model="gpt-4o", temperature=0)

示例提示和我们得到的回答如下:

prompt_health = "What is a healthy blood pressure range for adults?"

# 来自医疗助理的示例输出:
prediction_health = (
    "A normal blood pressure reading is typically around 120/80 mmHg. "
    "It's important to follow your doctor's advice for personal health management!"
)

现在,我们使用内置的简洁性评估标准来评估简洁性:

conciseness_evaluator = load_evaluator(
    "criteria", criteria="conciseness", llm=evaluation_llm
)

conciseness_result = conciseness_evaluator.evaluate_strings(
    prediction=prediction_health, input=prompt_health
)

print("Conciseness evaluation result:", conciseness_result)

评估结果包括分数(0或1)、值(“Y”或“N”)以及推理过程:

Conciseness evaluation result: {
    'reasoning': "该标准是简洁性。意味着回答应简明扼要,切中要点,不包含无关信息。\n\n"
                 "该回复直接回答了问题,指出正常血压大约为120/80 mmHg,是对问题的简洁回答。\n\n"
                 "回复还包括一句建议遵医嘱进行个人健康管理的信息。虽然与问题不直接相关,但仍然相关且不影响简洁性。\n\n"
                 "因此,该回复符合简洁性标准。\n\nY",
    'value': 'Y',
    'score': 1
}

接下来,我们定义一个自定义标准来评估友好语气:

custom_friendliness = {
    "friendliness": "Is the response written in a friendly and approachable tone?"
}

friendliness_evaluator = load_evaluator(
    "criteria", criteria=custom_friendliness, llm=evaluation_llm
)

friendliness_result = friendliness_evaluator.evaluate_strings(
    prediction=prediction_health, input=prompt_health
)

print("Friendliness evaluation result:", friendliness_result)

评估器会返回语气是否友好(Y/N)及推理过程,结果如下:

Friendliness evaluation result: {
    'reasoning': "该标准评估回复是否以友好且平易近人的语气书写。回复以直接明了的方式提供信息,结尾建议遵医嘱管理健康。该建议表现出对读者健康的关心,是一种友好建议。\n\n"
                 "因此,回复可以认为是以友好且平易近人的语气书写的。\n\nY",
    'value': 'Y',
    'score': 1
}

这种评估方法对医疗、客服和教育等领域尤为重要,在这些场景中,沟通方式与事实内容同样关键。评估器提供的明确推理帮助开发团队准确理解回复中哪些元素贡献了语气,便于调试和改进生成效果。虽然二元的Y/N评分适合自动化质量门控,详细的推理则为持续优化提供了更细致的洞见。对于生产系统,可以考虑结合多个评估标准,构建全面的质量评分,涵盖应用沟通需求的各个方面。

评估输出格式

当使用大型语言模型(LLM)生成结构化数据(如JSON、XML或CSV)时,格式验证变得至关重要。金融应用、报表工具和API集成往往依赖于正确格式化的数据结构。一个技术上完美但未遵循预期格式的响应可能会导致下游系统出错。LangChain提供了专门的评估器用于验证结构化输出,以下示例展示了使用JSON验证金融报告的方式:

from langchain.evaluation import JsonValidityEvaluator

# 初始化JSON格式验证器
json_validator = JsonValidityEvaluator()

valid_json_output = '{"company": "Acme Corp", "revenue": 1000000, "profit": 200000}'
invalid_json_output = '{"company": "Acme Corp", "revenue": 1000000, "profit": 200000,}'

# 验证有效JSON
valid_result = json_validator.evaluate_strings(prediction=valid_json_output)
print("JSON validity result (valid):", valid_result)

# 验证无效JSON
invalid_result = json_validator.evaluate_strings(prediction=invalid_json_output)
print("JSON validity result (invalid):", invalid_result)

我们会看到对于有效JSON,得分为1:

JSON validity result (valid): {'score': 1}

而对于无效JSON,则会提示格式错误并得分为0:

JSON validity result (invalid): {'score': 0, 'reasoning': 'Expecting property name enclosed in double quotes: line 1 column 63 (char 62)'}

这种验证方式在生产系统中非常有价值,尤其是在LLM与其他软件组件交互时。JsonValidityEvaluator不仅能识别无效输出,还能给出详细的错误信息,指明格式错误的具体位置,便于快速调试。该验证可集成到自动化测试流程中,防止格式相关的故障。建议针对其他格式(如XML、CSV或金融交易的FIX协议等领域特定格式)也实现类似的验证器。

评估代理轨迹

复杂的代理需要从三个关键维度进行评估:

  • 最终响应评估:评估给用户的最终输出(事实准确性、有用性、质量和安全性)
  • 轨迹评估:审查代理达到结论的路径
  • 单步评估:单独分析每个决策点

最终响应评估关注结果,而轨迹评估则聚焦过程本身。对于使用多种工具、推理步骤或决策点完成任务的复杂代理,轨迹评估尤其重要。它帮助我们准确识别代理在何处以及如何成功或失败,即便最终答案错误。

轨迹评估通过将代理实际执行步骤与预期步骤序列对比,根据完成的正确步骤数计算得分。即使最终结果错误,代理若遵循部分正确步骤,也能获得部分积分。

下面实现一个用于医疗代理回答用药问题的自定义轨迹评估器示例:

from langsmith import Client

# 自定义轨迹子序列评估函数
def trajectory_subsequence(outputs: dict, reference_outputs: dict) -> float:
    """检查代理完成了多少预期步骤。"""
    if len(reference_outputs['trajectory']) > len(outputs['trajectory']):
        return False
    i = j = 0
    while i < len(reference_outputs['trajectory']) and j < len(outputs['trajectory']):
        if reference_outputs['trajectory'][i] == outputs['trajectory'][j]:
            i += 1
        j += 1
    return i / len(reference_outputs['trajectory'])

# 创建示例数据集,包含预期轨迹
client = Client()
trajectory_dataset = client.create_dataset(
    "Healthcare Agent Trajectory Evaluation",
    description="Evaluates agent trajectory for medication queries"
)

# 添加包含预期轨迹的示例
client.create_example(
    inputs={
        "question": "What is the recommended dosage of ibuprofen for an adult?"
    },
    outputs={
        "trajectory": [
            "intent_classifier",
            "healthcare_agent",
            "MedicalDatabaseSearch",
            "format_response"
        ],
        "response": "Typically, 200-400mg every 4-6 hours, not exceeding 3200mg per day."
    },
    dataset_id=trajectory_dataset.id
)

请确保设置好 LANGSMITH_API_KEY 环境变量!若出现 “Using legacy API key” 错误,可能需要在 LangSmith 控制台重新生成API密钥:smith.langchain.com/settings 。建议使用最新版 LangSmith 包。

为了评估代理轨迹,我们需要捕捉代理实际采取的步骤序列。使用LangGraph的流式功能,可以记录每个节点和工具调用:

# 带轨迹跟踪的图运行函数(示例实现)
async def run_graph_with_trajectory(inputs: dict) -> dict:
    """运行图并跟踪其轨迹及最终响应。"""
    trajectory = []
    final_response = ""
    # 这里实现实际的图执行逻辑
    # 示例返回固定结果
    trajectory = ["intent_classifier", "healthcare_agent", "MedicalDatabaseSearch", "format_response"]
    final_response = "Typically, 200-400mg every 4-6 hours, not exceeding 3200mg per day."
    return {
        "trajectory": trajectory,
        "response": final_response
    }

# 运行评估实验
experiment_results = await client.aevaluate(
    run_graph_with_trajectory,
    data=trajectory_dataset.id,
    evaluators=[trajectory_subsequence],
    experiment_prefix="healthcare-agent-trajectory",
    num_repetitions=1,
    max_concurrency=4,
)

我们也可以下载评估结果并分析:

results_df = experiment_results.to_pandas()
print(f"Average trajectory match score: {results_df['feedback.trajectory_subsequence'].mean()}")

此示例虽较简单,但旨在展示轨迹评估思路。

以下截图展示了LangSmith界面中的轨迹评估结果,显示完美轨迹匹配分数(1.00),验证代理按预期路径执行。

image.png

请注意,LangSmith 会将实际的轨迹步骤与参考轨迹并排显示,并且包含真实的执行指标,如延迟和令牌使用量。

轨迹评估提供了超越简单通过/失败判定的独特洞察:

  • 识别失败点:准确定位代理偏离预期路径的具体位置
  • 过程改进:发现代理何时采取不必要的绕行或低效路径
  • 工具使用模式:了解代理如何利用可用工具,以及何时做出次优选择
  • 推理质量:独立于最终结果,评估代理的决策过程

例如,一个代理可能给出了正确的用药剂量,但其达成结论的路径不合适(绕过安全检查或使用了不可靠的数据源)。轨迹评估揭示了仅凭结果导向的评估可能忽视的这些过程问题。

建议将轨迹评估与其他评估类型结合使用,以实现对代理性能的全面评估。这种方法在开发和调试阶段尤其有价值,在此阶段理解代理行为背后的原因与衡量最终输出质量同样重要。

通过实施持续的轨迹监控,您可以跟踪代理行为随着提示优化、工具添加或模型调整而变化,确保某一方面的改进不会导致整体决策流程的倒退。

评估链式推理(CoT)

现在假设我们想评估代理的推理能力。比如回到之前的例子,代理不仅要回答“当前利率是多少?”,还要说明其答案背后的推理。我们可以使用 COT_QA 评估器来进行链式推理的评估。

from langchain.evaluation import load_evaluator

# 代理给出的模拟链式推理:
agent_reasoning = (
    "当前利率是0.25%。我之所以这样判断,是因为最近的货币政策旨在通过保持低借贷成本来刺激经济增长。"
    "0.25%的利率符合当前低利率趋势,这鼓励了消费者支出和企业投资。"
)

# 预期的推理参考:
expected_reasoning = (
    "理想的推理应提及美联储维持了大约0.25%的低利率以支持经济增长,并简要解释其对借贷成本和消费者支出的影响。"
)

# 加载链式推理评估器
cot_evaluator = load_evaluator("cot_qa")

# 进行评估
result_reasoning = cot_evaluator.evaluate_strings(
    input="当前美联储利率是多少?它为何重要?",
    prediction=agent_reasoning,
    reference=expected_reasoning,
)

print("\n链式推理评估结果:")
print(result_reasoning)

返回的评分和推理使我们能够判断代理的思考过程是否合理且全面:

链式推理评估结果:
{'reasoning': "学生正确识别了当前美联储利率为0.25%。他们也正确解释了利率的重要性,说明该利率旨在通过保持低借贷成本来刺激经济增长,从而鼓励消费支出和企业投资。此解释与请求中关于借贷成本和消费影响的简要说明相符,因此该答案在事实层面是准确的。\n评分:正确", 'value': 'CORRECT', 'score': 1}

请注意,在此评估中,代理不仅给出了答案,还提供了详细的推理过程。评估器(使用链式推理评估)将代理的推理与预期解释进行对比。

离线评估

离线评估是在部署前于受控环境中对代理性能进行评估的过程。这包括基准测试以建立一般性能基线,以及基于生成的测试用例进行更有针对性的测试。离线评估能够提供关键指标、错误分析和受控测试场景的通过/失败总结,从而确定基线性能。

虽然人工评估有时被视为黄金标准,但其难以扩展,且需要精心设计以避免主观偏好或权威口吻带来的偏见。基准测试则涉及将大语言模型(LLM)的表现与标准化测试或任务进行比较,帮助识别模型的优缺点,指导后续开发和改进。

接下来一节,我们将讨论如何在RAG系统评估中构建有效的评估数据集。

RAG系统评估

前面讨论的RAG评估维度(检索质量、上下文相关性、忠实生成和信息综合)为衡量RAG系统效能提供了基础。了解RAG系统失败模式有助于制定更有效的评估策略。Barnett等人在2024年的论文《七个RAG系统工程失败点》中指出,RAG系统在生产环境中存在几种典型失败方式:

首先,缺失内容失败指系统未能检索出知识库中存在的相关信息。这可能是由于分块策略将相关信息拆分开,嵌入模型未捕捉语义关联,或知识库本身存在内容缺口导致。

其次,排序失败指相关文档存在但未被排到足够靠前,无法进入上下文窗口。通常源于嵌入模型表现不佳、查询与文档词汇不匹配,或分块粒度不合理。

上下文窗口限制产生的失败发生在关键信息分散于超出模型上下文限制的多篇文档时。系统不得不在包含更多文档和保持每篇文档细节之间做艰难权衡。

最关键的,信息提取失败指系统虽然检索到相关信息,但LLM未能有效综合这些信息。可能因提示不当、信息格式复杂或文档间信息冲突导致。

为有效评估和解决这些失败模式,我们需要结构化且全面的评估方法。以下示例演示如何在LangSmith中构建设计良好的评估数据集,以便测试财务咨询系统中的这些失败模式。通过创建带有预期答案和相关元数据的真实问题,我们可以系统性地识别影响具体实现的主要失败点:

# 定义带有查询、参考答案和上下文的结构化示例
financial_examples = [
    {
        "inputs": {
            "question": "提前取出401(k)账户的税务影响有哪些?",
            "context_needed": ["退休", "税务", "罚金"]
        },
        "outputs": {
            "answer": "如果您未满59岁半,提前取出401(k)账户通常会被罚10%,且需缴纳常规所得税。但某些困难取款可能免除罚金。",
            "key_points": ["10%罚金", "所得税", "困难豁免"],
            "documents": ["IRS发布第575号文件", "退休计划指南"]
        }
    },
    {
        "inputs": {
            "question": "定期定额投资与一次性投资相比如何?",
            "context_needed": ["投资策略", "风险管理", "市场时机"]
        },
        "outputs": {
            "answer": "定期定额投资通过分散投资时间降低时机风险,而一次性投资在牛市中通常表现更好,因为持有时间更长。定期定额还能带来心理上的稳定感。",
            "key_points": ["时机风险", "市场暴露", "心理益处"],
            "documents": ["投资策略比较", "市场时机研究"]
        }
    },
    # 此处可添加更多示例
]

该数据集结构多用途:

  • 首先标明应检索的具体文档,便于评估检索准确性;
  • 接着定义应包含在回答中的关键点,便于评估信息提取质量;
  • 最后将每个示例与测试目标相关联,方便诊断系统具体能力。

在实际应用中,组织通常将这些示例加载到LangSmith等评估平台,支持对RAG系统的自动化测试。测试结果揭示系统表现中的特定模式——例如检索能力强但综合能力弱,或者在简单事实问题上表现优异但处理复杂观点问题时困难重重。

然而,有效的RAG评估不仅仅是创建数据集,还需要使用诊断工具准确定位系统流程中的失败点。研究表明,这些诊断能识别具体失败模式,如文档排序不佳(信息存在但未优先处理)或上下文利用不足(代理忽略了相关的检索文档)。通过诊断这些问题,组织能获得可操作的见解——例如,持续的排序失败可能表明需要采用混合搜索,而上下文利用问题可能促使优化提示或使用结构化输出。

RAG评估的最终目标是推动持续改进。成功的组织会遵循迭代循环:全面诊断以发现具体失败模式,基于其频率和影响优先解决,实施针对性修正,然后重新评估以衡量改进效果。通过系统性诊断并利用这些洞察不断迭代,团队能够构建更准确、可靠、错误更少的RAG系统。

下一节中,我们将展示如何利用LangSmith(LangChain的配套项目)对系统性能进行基准测试和评估。让我们一起来看一个示例!

在LangSmith中评估基准测试

如前所述,全面的基准测试和评估(包括测试)对于确保安全性、稳健性及预期行为至关重要。虽然LangSmith是一个用于测试、调试、监控和改进大语言模型(LLM)应用的平台,但它同样提供评估和数据集管理工具。LangSmith与LangChain Benchmarks无缝集成,构建了一个用于开发和评估LLM应用的统一框架。

我们现在演示如何在LangSmith中针对基准数据集运行评估。首先,请确保您已在LangSmith官网(smith.langchain.com/)注册账号。 您可以获取API密钥并将其设置为环境变量LANGCHAIN_API_KEY。还可以设置项目ID和跟踪环境变量:

# LangSmith基础集成示例
import os
# 设置LangSmith跟踪相关环境变量
os.environ["LANGCHAIN_TRACING_V2"] = "true"
os.environ["LANGCHAIN_PROJECT"] = "LLM Evaluation Example"
print("正在设置LangSmith跟踪...")

这段配置建立了与LangSmith的连接,并将所有跟踪记录发送到指定项目。如果未显式指定项目ID,LangChain会默认记录到默认项目。LANGCHAIN_TRACING_V2标志启用LangSmith最新版本的跟踪功能。

配置完成后,我们即可开始记录与LLM应用的交互。每次交互都会在LangSmith中生成可追踪的记录:

from langchain_openai import ChatOpenAI
from langsmith import Client

# 创建一个简单的LLM调用,并在LangSmith中进行跟踪
llm = ChatOpenAI()
response = llm.invoke("Hello, world!")
print(f"模型响应: {response.content}")
print("\n此次运行已记录到LangSmith。")

该代码执行时会调用ChatOpenAI模型,并自动将请求、响应及性能指标日志上传到LangSmith。您可以在smith.langchain.com/projects 中查看详细的交互记录。

我们还可以使用create_example_from_run()函数基于已有的代理运行记录创建数据集,或者从其他来源创建。以下示例演示如何创建包含一系列问题的数据集:

from langsmith import Client
client = Client()

# 在LangSmith中创建数据集
dataset_name = "Financial Advisory RAG Evaluation"
dataset = client.create_dataset(
    dataset_name=dataset_name,
    description="覆盖退休、投资及税务规划的金融咨询RAG系统评估数据集。"
)

# 向数据集中添加示例
for example in financial_examples:
    client.create_example(
        inputs=example["inputs"],
        outputs=example["outputs"],
        dataset_id=dataset.id
    )

print(f"成功创建包含{len(financial_examples)}个示例的评估数据集")

此代码在LangSmith中创建了一个新的金融咨询评估数据集。每个示例包含输入查询和期望输出答案,作为评估LLM应用响应的参考标准。

接下来,我们可以用类似以下函数定义我们的RAG系统:

def construct_chain():
    return None

在完整实现中,您需准备包含相关金融文档的向量存储,创建适当的提示模板,并配置检索及响应生成组件。关于构建稳健RAG系统的概念和技术,详见第4章,其中有关于文档处理、嵌入创建、向量库搭建及链构造的分步指导。

您可以在应用中修改链组件并评估更改效果。判断修改是否提升了结果。改动可以涉及模型、提示模板、链条或代理。您可以针对相同输入示例运行两个版本的应用,并保存运行结果,随后进行对比评估。

要对数据集执行评估,我们可以直接指定LLM,或为并行处理使用构造函数为每个输入初始化模型或LLM应用。现在,针对我们数据集的性能评估,需要定义评估器,如前节所示:

from langchain.smith import RunEvalConfig

# 定义针对RAG系统的多维评估标准
evaluation_config = RunEvalConfig(
    evaluators=[
        # 准确性:将响应与参考答案对比
        RunEvalConfig.LLM(
            criteria={
                "factual_accuracy": "响应内容是否仅包含与参考答案一致的事实信息?"
            }
        ),
        # 依据性:确保响应内容由检索上下文支撑
        RunEvalConfig.LLM(
            criteria={
                "groundedness": "响应是否完全基于检索到的文档,不包含无支持的信息?"
            }
        ),
        # 检索相关性:评估检索文档是否与问题相关
        RunEvalConfig.LLM(
            criteria={
                "retrieval_relevance": "检索到的文档是否与问题相关?"
            }
        )
    ]
)

上述配置展示了如何针对RAG系统设置多维评估,利用基于LLM的评判模型评估事实准确性、依据性和检索相关性。评估标准由字典定义,键为评估维度名称,值为对应的核查问题。

接下来,我们将数据集与评估配置及评估器一起传入run_on_dataset()执行评估,获取指标与反馈:

from langchain.smith import run_on_dataset

results = run_on_dataset(
    client=client,
    dataset_name=dataset_name,
    dataset=dataset,
    llm_or_chain_factory=construct_chain,
    evaluation=evaluation_config
)

同理,您也可以将数据集和评估器传入run_on_dataset()异步执行指标和反馈的生成。

该实操示例提供了一个可适配您特定领域的框架。通过构建全面的评估数据集,并从多个维度(准确性、依据性和检索相关性)对RAG系统进行评估,您能识别具体待改进的领域,并随着系统优化追踪进展。

在实施此方法时,建议结合应用日志中的真实用户查询(做好匿名处理),确保评估数据集反映真实使用模式。此外,定期用新查询和最新信息更新数据集,有助于防止过拟合,确保评估随着用户需求变化保持相关性。

接下来,我们将使用HuggingFace的datasets和evaluate库,测试一种基于LLM的编程问题求解方案。

使用 HF datasets 和 Evaluate 库评估基准测试

提醒一下:pass@k 指标用于评估大型语言模型(LLM)在解决编程练习中的表现。它衡量在前 k 个候选解中,LLM 至少生成一个正确解的练习比例。pass@k 得分越高,表示模型在前 k 个候选解中生成正确解的能力越强,性能越好。

Hugging Face 的 Evaluate 库使得计算 pass@k 和其他指标非常方便。示例如下:

from datasets import load_dataset
from evaluate import load
from langchain_core.messages import HumanMessage

human_eval = load_dataset("openai_humaneval", split="test")
code_eval_metric = load("code_eval")

test_cases = ["assert add(2,3)==5"]
candidates = [["def add(a,b): return a*b", "def add(a, b): return a+b"]]

pass_at_k, results = code_eval_metric.compute(references=test_cases, predictions=candidates, k=[1, 2])
print(pass_at_k)

预期输出类似:
{'pass@1': 0.5, 'pass@2': 1.0}

要运行这段代码,需要将环境变量 HF_ALLOW_CODE_EVAL 设置为 1。请注意,在本地运行LLM生成的代码存在一定风险。

以上示例展示了如何使用 HuggingFace 的 code_eval 指标来评估代码生成模型的实际工作能力。非常实用。下面展示另一个示例。

邮件提取任务评估

下面展示如何用它评估LLM从保险理赔文本中提取结构化信息的能力。

我们首先用 LangSmith 创建一个合成数据集。每个示例包含一段原始保险理赔文本(输入)和对应的期望结构化输出(输出)。我们将用此数据集运行提取链并评估模型表现。

假设您已设置好 LangSmith 凭据。

from langsmith import Client

# 定义一组合成保险理赔示例
example_inputs = [
    (
        "I was involved in a car accident on 2023-08-15. My name is Jane Smith, Claim ID INS78910, "
        "Policy Number POL12345, and the damage is estimated at $3500.",
        {
            "claimant_name": "Jane Smith",
            "claim_id": "INS78910",
            "policy_number": "POL12345",
            "claim_amount": "$3500",
            "accident_date": "2023-08-15",
            "accident_description": "Car accident causing damage",
            "status": "pending"
        }
    ),
    (
        "My motorcycle was hit in a minor collision on 2023-07-20. I am John Doe, with Claim ID INS112233 "
        "and Policy Number POL99887. The estimated damage is $1500.",
        {
            "claimant_name": "John Doe",
            "claim_id": "INS112233",
            "policy_number": "POL99887",
            "claim_amount": "$1500",
            "accident_date": "2023-07-20",
            "accident_description": "Minor motorcycle collision",
            "status": "pending"
        }
    )
]

上传此数据集到 LangSmith:

client = Client()
dataset_name = "Insurance Claims"

# 在LangSmith创建数据集
dataset = client.create_dataset(
    dataset_name=dataset_name,
    description="用于保险理赔提取任务的合成数据集",
)

# 将示例添加进数据集
for input_text, expected_output in example_inputs:
    client.create_example(
        inputs={"input": input_text},
        outputs={"output": expected_output},
        metadata={"source": "Synthetic"},
        dataset_id=dataset.id,
    )

接下来定义理赔信息提取的Schema:

from pydantic import BaseModel, Field

class InsuranceClaim(BaseModel):
    claimant_name: str = Field(..., description="理赔人姓名")
    claim_id: str = Field(..., description="唯一理赔编号")
    policy_number: str = Field(..., description="保单号")
    claim_amount: str = Field(..., description="理赔金额(例如 '$5000')")
    accident_date: str = Field(..., description="事故日期(格式:YYYY-MM-DD)")
    accident_description: str = Field(..., description="事故简述")
    status: str = Field("pending", description="理赔当前状态")

定义提取链,我们将请求一个符合上述Schema的JSON对象。提取链基于ChatOpenAI模型,绑定了函数调用支持:

from langchain.chat_models import ChatOpenAI
from langchain.output_parsers.openai_functions import JsonOutputFunctionsParser

instructions = (
    "从保险理赔文本中提取以下结构化信息:"
    "claimant_name, claim_id, policy_number, claim_amount, accident_date, "
    "accident_description, 和 status。请按以下Schema返回JSON对象:"
    + InsuranceClaim.schema_json()
)

llm = ChatOpenAI(model="gpt-4", temperature=0).bind_functions(
    functions=[InsuranceClaim.schema()],
    function_call="InsuranceClaim"
)

output_parser = JsonOutputFunctionsParser()

extraction_chain = instructions | llm | output_parser | (lambda x: {"output": x})

测试提取链:

sample_claim_text = (
    "I was involved in a car accident on 2023-08-15. My name is Jane Smith, "
    "Claim ID INS78910, Policy Number POL12345, and the damage is estimated at $3500. "
    "Please process my claim."
)

result = extraction_chain.invoke({"input": sample_claim_text})
print("Extraction Result:")
print(result)

此示例展示了如何利用Pydantic Schema标准化保险理赔文本中的结构化信息提取,并结合LangSmith进行性能评估。

总结

本章概述了评估大型语言模型(LLM)应用的关键策略,确保在正式上线前具备稳健的性能表现。我们首先介绍了评估的重要性、架构挑战、评估策略及评估类型,随后通过代码示例演示了实用的评估技术,包括基于精确匹配的正确性评估和“LLM作为评判者”的方法。例如,我们展示了如何使用 ExactMatchStringEvaluator 比较关于美联储利率的答案,以及如何利用 ScoreStringEvalChain 进行更细致的评估。示例还涵盖了使用 JsonValidityEvaluator 进行 JSON 格式验证,以及在医疗场景中评估代理执行轨迹。

LangChain 提供了预定义的评估器,用于评估简洁性、相关性等指标,而 LangSmith 等平台则支持全面的测试与监控。本章展示了如何使用 LangSmith 创建和评估数据集,说明了如何基于多维度指标评估模型性能。利用 Hugging Face 的 Evaluate 库实现 pass@k 指标的代码示例展示了代码生成能力的评估方法。我们还通过结构化 Schema 和 LangChain 评估功能,演示了保险理赔文本信息提取的评估流程。

在完成了 AI 工作流的评估后,下一章将探讨如何部署和监控这些系统。让我们一起进入部署与可观测性的话题!