尧图建网站 尧图建网站 YAOTU WEB BUILD 免费咨询
ARTICLE DETAIL

资讯详情

深耕网站建设与建站编程的一线实战洞察。

Test-Time Scaling新思路:Verifier-Free与Consilience机制解析

Test-Time Scaling新思路:Verifier-Free与Consilience机制解析 最近很多团队都在讨论 Test-Time Scaling测试时扩展一个常见的落地姿势是让模型多采样几个答案然后从中挑一个最好的。这个“挑一个最好的”动作决定了 TTS 项目的天花板。挑最好的最经典方式是 Best-of-N采样 N 个结果再用一个 verifier 给每个结果打分。问题是verifier 本身要训练、要标注、要防奖励黑客要在主模型迭代后重新校准。把这些成本算进去TTS 的工程门槛一下就高了起来。于是一个更值得关注的方向浮出水面Verifier-Free Test-Time Scaling。它不训练专用验证器而是靠采样过程自身产生的多条证据线来选择答案。这套机制的核心正是本文标题里的Consilience——多条彼此独立的证据线同向会聚到同一个结论时这个结论往往比单条推理链更可靠。这篇文章会分三块展开先解释 Test-Time Scaling 为什么离不开筛选Verifier 路线又贵在哪里再拆解 Consilience 的原理和主流实现方法最后给出一份可以直接运行的 Python 示例完整覆盖采样、答案归一化、自评、多信号聚合并给出常见问题与工程建议。1. 为什么 Test-Time Scaling 需要一种新的筛选机制Test-Time Scaling 的含义简单说就是在推理阶段投入更多计算量换取模型在困难任务上的表现提升。它和传统的 Scaling 有一个很本质的区别传统 Scaling 是把算力花在训练上让模型参数变大、数据变多最终让模型“本身变强”。Test-Time Scaling 是把算力花在推理上让模型在回答问题时多想几步、多试几条路径最终让“这一次的回答更可靠”。常见的 Test-Time Scaling 有三种实现方式多次采样加投票让模型用非零温度生成多个答案再通过自洽性投票Self-Consistency选出最终答案。扩展思维链让模型在回答前先生成更长的思考过程类似 o1 系列的长思维链模式。搜索式生成在推理过程中维护多条候选路径做 beam search 或 tree search再用某种信号剪枝和选择。这三种方式都有一个共同点候选变多了但没人告诉你哪个候选是对的。如果只看表面很多人会以为“多采样几次哪个答案出现的次数多就选哪个”就够了。但这个问题在实践中远比想象中复杂模型的错误未必是随机分散的可能出现系统性偏向多个采样都落在同一个错误答案上。答案的表达方式不统一例如“17”“$17”“17 dollars”如果不好好归一化同一个正确答案会被拆成多个桶反而拉低票数。简单任务中所有采样几乎一致多次采样只是浪费成本而高难度任务中模型可能所有候选都不对投票只是选出一个“错得比较像样”的答案。所以TTS 的价值很容易理解但它的收益上限是由“筛选机制”决定的。如果你只是随机采样然后盲目取众数那大概率得不到理想的结果。这里出现了一个关键问题筛选信号从哪里来传统的答案是训练一个专门的验证器。而 Verifier-Free 的思路是不用外部验证器用采样过程内部的多维信号做筛选。这正是下一节要展开的内容。2. Verifier 路线为什么贵Verifier-Free 为什么出现2.1 Verifier 是什么Verifier 在 TTS 流程里扮演的角色类似于“裁判”。你采样出了 N 条候选推理链和答案每一条都需要一个分值分数最高的那条被选中输出。裁判可以是三种形态ORMOutcome Reward Model结果奖励模型只看最终结果对不对给整个答案打个分。PRMProcess Reward Model过程奖励模型对推理过程的每一步进行打分训练成本更高但能定位错误步骤。LLM-as-a-Judge不训练专门的模型而是用更强的 LLM 扮演裁判按提示词规则给候选答案打分。2.2 Verifier 路线的四个现实问题Verifier 路线在学术评测中表现很好但在工程项目中会遇到四个实实在在的坑第一标注成本高。训练 ORM 需要大量“输入-答案-质量分”数据训练 PRM 更麻烦需要对每一步进行过程级标注。这种标注在数学题上还能做到了开放域、代码、多轮对话场景人工标注的质量和一致性很难保证。第二奖励黑客Reward Hacking。验证器是另一个模型它会找到自己的捷径。比如学到“答案越长分数越高”“只要出现某些关键词就给高分”而不是真正理解推理质量。采样结果经过这种验票器之后选出来的往往是“看起来很有道理但实际跑不通”的答案。第三跨分布泛化差。验证器是在特定分布上训练的换一个数据集、换一个领域、甚至换一个主模型它的打分能力都会下降。比如在 GSM8K 上训练的 PRM拿到代码生成任务上基本不能用需要重新训练或者重新标注。第四维护成本高。主模型升级后验证器分数分布会漂移。原来阈值是 0.8升级后可能变成 0.6需要重新校准。这等于每一个模型版本都要额外维护一个裁判系统。2.3 Verifier-Free 是什么Verifier-Free 不是“不筛选”而是把筛选信号从外部模型换成采样过程本身的内部信息。它不需要训练额外的参数判断依据来自以下几个方面模型自己在不同温度下采样出的答案是否集中在同一个结果上。生成某个答案时模型自身的 token 级置信度是高还是低。让模型对自己刚生成的答案做二次检查或自评打分是否和频率信号一致。答案是否满足任务本身的硬约束比如必须是数字、必须是合法 JSON。这些信号单独看都不可靠但当多条证据线同时指向同一个答案时它们叠加起来可以接近甚至超过一个训练好的 verifier。我们可以把两条路线放在一张表里对比对比维度Verifier 路线Verifier-Free 路线信号来源额外训练的评分模型采样过程内部的多维信号训练成本高需要标注和调优无完全复用主模型能力奖励黑客风险存在需要持续对抗较低信号更贴近推理过程本身跨分布泛化差换领域需要重新训练较好不依赖固定训练分布工程维护主模型升级后需要校准 verifier只需调整 prompt 和聚合逻辑适合场景发布固定任务、对效果要求极高的场景快速验证、多任务、模型频繁迭代的场景这个对比给我们的判断是Verifier-Free 不是来取代 verifier 的而是先把高门槛的 verifier 步骤拿掉让 TTS 成为大多数团队都能用得起的工程方案。它的价值不在于“比 verifier 更准”而在于“在不行使 verifier 的情况下还能得到一个足够好的选择机制”。3. Consilience 的核心机制多条证据线同向会聚3.1 概念从哪里来Consilience 这个词来自科学哲学爱德华·威尔逊曾写过一本著名的书《知识大融通》核心思想是如果多个不同来源的证据都指向同一个结论那么这个结论的可信度会大大提高。比如考古学、基因学、语言学从三个不同角度同时证明某个迁徙路线存在那就不太可能只是巧合。在 Test-Time Scaling 里我们可以借用这个思想当多个相对独立的推理信号都指向同一个候选答案时这个答案的可信度显著上升即使我们没有一个专门训练的验证器也能做出可靠选择。3.2 在 TTS 里的技术含义如果用更工程化的语言描述Consilience 指的是下面这个过程对同一个问题模型生成 N 条候选解答。针对每条候选解答我们收集几类信号答案频率多条独立采样路径最终落在同一个答案上的比例。路径自洽性推理链之间是否有关键的公共步骤或公共结论。生成置信度模型在生成该答案时token 级对数概率的平均值或熵值。自评信号让模型对这条解答做二次评估给出一个质量分。约束一致性答案是否满足问题的硬性约束比如单位、范围、格式。这些信号来自不同角度彼此是相对独立的。如果它们各自都有噪声那么单看任何一个都很容易被带偏但如果它们同时指向同一个答案就构成了一种“证据汇聚”这种汇聚可以看作一个无需学习参数的置信度估计器。3.3 和 Self-Consistency 的关系很多人会问这不是 Self-Consistency 吗两者确实有关系但有明显区别Self-Consistency 是 2022 年提出的经典方法它只用了“答案频率”这一条信号采样 N 次做多数投票。它本质上是 Consilience 的一个特例证据线只有一条。Consilience 在实现上会把频率、置信度、自评、约束检查等多条信号做加权融合并且针对每条候选答案计算一个综合分而不是简单看谁票多。这里真正容易犯错的地方在于多数投票有一个隐含假设那就是错误的答案必须“足够分散”。如果模型存在系统性偏向比如 10 次采样里有 6 次都因为同一个误区得出同一个错误答案多数投票就会堂而皇之地选出错误答案。而 Consilience 的思路是用其他证据线来对冲这种“投票幻觉”。当某个答案虽然频率高但模型自评分数低、生成置信度也低时综合分会被压下去给其他答案留下竞争空间。一句话总结Self-Consistency 是“谁票多选谁”Consilience 是“谁获得的独立证据支持最多选谁”。4. Verifier-Free TTS 主流方法盘点在实际项目里Verifier-Free TTS 已经有几种比较成熟的做法。它们的区别主要在于用哪些内部信号、如何把这些信号组合成最终选择。4.1 Self-Consistency自洽性投票这是最基础的 Verifier-Free 方法。流程非常简单用非零温度采样 N 次。对答案做归一化处理。统计每个答案的出现次数。选择出现次数最多的答案。优点是零训练成本实现简单作为基线非常合适。缺点是只用了频率信号遇到系统性偏向时效果下降。4.2 基于生成概率的加权投票在采样的时候如果接口支持返回 token 级 logprob我们可以计算每条候选解答的平均对数概率。平均对数概率越高说明模型生成这条答案时越“自信”。加权投票的公式通常是最终得分 频率权重 × 票数比例 置信度权重 × 归一化后的平均对数概率这种方法比纯投票多了一条证据线在答案分布接近的情况下能打破平局。需要注意的是不同模型返回 logprob 的方式差异很大很多开源模型的 API 不一定支持逐 token 概率所以这个信号要用“拿得到就加权拿不到就降低权重”的容错策略。4.3 自评与二次检查让模型对自己生成的答案重新审视一遍并给出一个质量分。这个思路很直观但也容易被误解。单纯把自评分当成终极标准是不可靠的因为同一个模型的审题能力和推理能力是同一个能力上限它答错的时候往往也意识不到哪里错。更好的用法是把自评当作多个证据线之一和频率、置信度融合。实践中自评也有两种形态打分式给候选答案打 0 到 10 分。反思式让模型先指出候选答案是否有错误如果有错误再重新生成。打分式更适合后面做信号融合反思式更适合在搜索流程里做剪枝。4.4 搜索式采样加启发式剪枝比较重的 Verifier-Free 方案是树搜索或 beam search。每生成一小步就用启发式规则决定是否保留这条分支。启发式规则可以是当前分支的 token 平均熵是否过高。是否已经出现逻辑矛盾。是否偏离了题目约束。这种方案可以显著降低无效探索但实现复杂度高一般只有在采样成本很高、推理链又比较长的时候才值得做。4.5 多信号同向聚合Consilience 式思路这是本文示例代码采用的方式。它把以上多种信号统一到一个可配置的加权公式里对每条候选答案求综合分Consilience Score w1 × 答案频率得分 w2 × 生成置信度得分 w3 × 自评得分 w4 × 约束一致性得分权重可以根据任务调节。这个方式最接近生产环境的需求既不会因为单一信号失真又不需要训练额外模型。做一个总体的方法对比方法使用信号优点缺点工程成本Self-Consistency答案频率实现简单基线稳定对系统性偏向不敏感低概率加权投票频率 token 置信度多一条证据线打破平局很多接口拿不到 logprob低自评/反思模型自评分数能缓解投票幻觉单独使用不够可靠低搜索式采样过程启发式探索效率高实现复杂调参繁琐高多信号同向聚合频率 置信度 自评 约束综合性强抗单点失效需要设计融合公式中对多数团队来说建议的切入路径是先用 Self-Consistency 跑通基线再逐步加入置信度和自评信号。不要一上来就上树搜索那样会把主要精力消耗在工程调试上而不是任务本身。5. 环境准备与实验任务设计5.1 运行环境本文示例代码使用 Python建议版本 3.9 或以上。代码通过 OpenAI 兼容接口调用模型这意味着你可以使用 OpenAI 官方 API也可以把调用地址切换到本地部署的 vLLM、Ollama 等推理服务只需要修改base_url和模型名。示例代码中不会把 API Key 硬编码写进去而是从环境变量读取export OPENAI_API_KEYyour_api_key export MODEL_NAMEgpt-4o-mini如果你使用的是本地模型可以这样设置export OPENAI_BASE_URLhttp://localhost:8000/v1 export MODEL_NAMEyour-local-model注意OPENAI_BASE_URL是一个约定的环境变量名OpenAI Python SDK 会自动读取它作为base_url。如果你用的不是 OpenAI SDK 而是其他兼容库请以对应库的配置方式为准。5.2 依赖安装只需要两个核心依赖pip install openai如果你的环境里没有安装python-dotenv也可以加一个pip install openai python-dotenv这样可以用.env文件管理环境变量避免每次手动 export。5.3 实验任务设计为了演示 Verifier-Free TTS我们需要一个“答案可以自动判定、推理过程有一定长度、存在常见错误分支”的任务。这里推荐先用数学应用题题目Alice 比 Bob 的年龄大 10 岁。5 年后两人年龄之和是 40 岁。 请问 Alice 现在多少岁这个题目正确答案是 20 岁。常见错误包括直接列方程出错得到 25。把“5年后年龄之和是40”错误理解成“现在年龄之和是40”得到 22.5 或 15。没有把 Alice 比 Bob 大 10 岁的条件用上得到 20 以外的一堆答案。这个任务的好处是不同错误分支会分散正确答案在多次采样中更容易形成稳定的多数同时可以用代码自动判断最终答案是否正确方便做效果验证。5.4 固定输出格式的重要性在开始写采样代码之前先想清楚一个问题答案归一化是整个流程最容易被低估的环节。模型输出的答案有多种写法“20”“20岁”“Alice 现在 20 岁”。如果以原始文本做聚合同一个正确答案会被切成多个桶导致票数分散。解决办法是在一开始就用 prompt 约束模型输出结构。我们在 system prompt 里明确要求模型你是一个严谨的推理助手。请一步步推理并在最后单独一行输出 最终答案答案这样在代码里就可以用正则表达式稳定提取最终答案把“20岁”“20”“20 岁”统一归一化成“20”。6. 核心流程拆解无验证器 TTS 流水线整个 Verifier-Free TTS 流水线可以分成六个步骤。每一步做错了都会直接影响最终答案质量。6.1 构造 Prompt这一步的目标是把“推理过程”和“最终答案”分离。System Prompt 固定模型行为User Prompt 放入具体题目。推荐格式你是一个严谨的推理助手。请一步步推理并在最后单独一行输出 最终答案答案这里的关键是“单独一行”和固定前缀。不要只用“请回答问题”这种模糊指令否则后面做归一化时会非常痛苦。6.2 多次采样采样数量建议从 8 次开始。采样温度建议在 0.6 到 0.8 之间。温度太低所有采样几乎一样采样没有意义温度太高模型会生成脱离题目的内容。n_samples 8 temperature 0.7在代码里我们会对每个样本单独调用一次模型接口而不是用n8的批量参数。原因是批量参数在部分兼容接口上不返回每条独立消息的详细信息不方便后续提取 logprob。6.3 答案归一化把模型输出里的最终答案提取出来并统一成标准形式。对数学题通常需要去掉货币符号、单位、语气词。将分数转成小数或者统一保留分数形式。把“第2个”“第二个”之类的中文序号转成数字。示例代码里实现了一个简化版归一化函数只提取最终答案后面的内容。生产环境建议用更健壮的规则比如结合正则和单位映射一起处理。6.4 信号采集这一步是 Verifier-Free TTS 的核心。对每条候选答案我们采集以下信号答案频率所有采样中相同答案出现的比例。生成置信度模型生成这条答案时的平均 token 对数概率。拿不到就打低权重。自评分数让模型对该答案做二次评分分值范围 0 到 10。约束一致性答案是否匹配任务硬约束比如必须是数字、必须是合法 JSON。自评分数这里有一点要注意如果对每一条候选答案都单独调用一次模型接口成本会翻倍。一个常见的优化是只对高频候选答案做自评忽略只出现一次的孤立答案。频率本身就是强信号不需要为低频噪声浪费成本。6.5 Consilience 打分把 6.4 的信号做标准化后加权求和。示例权重频率0.35 置信度0.15 自评0.30 约束0.20权重不是固定的。如果任务允许拿到 logprob可以调高置信度权重如果任务格式很严格可以调高约束权重。建议在一开始用默认权重跑通再用验证集微调。6.6 输出选择对每个唯一候选答案计算综合分选出分数最高的答案作为最终输出。同时把分数明细打印出来方便分析“为什么选了这个答案”。这个流程看起来很简单但真正的坑在细节。下面用完整代码演示一遍。7. 完整示例代码实现下面这份代码是完整的 Verifier-Free TTS 示例可以直接保存为verifier_free_tts.py运行。代码里分模块实现方便你按需修改。7.1 模型调用封装# 文件路径verifier_free_tts.py import os import re import json from collections import Counter from concurrent.futures import ThreadPoolExecutor from openai import OpenAI # 初始化客户端自动读取环境变量 client OpenAI( api_keyos.getenv(OPENAI_API_KEY), base_urlos.getenv(OPENAI_BASE_URL, None), ) MODEL os.getenv(MODEL_NAME, gpt-4o-mini) SYSTEM_PROMPT ( 你是一个严谨的推理助手。请一步步推理并在最后单独一行输出\n 最终答案答案 ) def call_model(messages, temperature0.0, want_logprobsFalse): 调用模型尽量获取 token 级对数概率。 返回 (response, has_logprobs) 两个值。 kwargs { model: MODEL, messages: messages, temperature: temperature, } if want_logprobs: try: resp client.chat.completions.create( **kwargs, logprobsTrue, top_logprobs3, ) return resp, True except Exception: # 接口不支持 logprobs 时降级为普通调用 pass resp client.chat.completions.create(**kwargs) return resp, False def get_text(resp): 从响应中取出文本内容。 return resp.choices[0].message.content.strip()注意top_logprobs参数在部分 OpenAI 兼容接口中不受支持所以这里用try/except包住。降级之后后面的置信度信号会被置为 None不影响主流程运行。7.2 采样与答案归一化def average_logprob(resp): 计算一条回答的平均 token 对数概率拿不到返回 None。 try: content resp.choices[0].logprobs.content if not content: return None logprobs [item.logprob for item in content if item.logprob is not None] if not logprobs: return None return sum(logprobs) / len(logprobs) except Exception: return None def extract_final_answer(text): 从模型输出中提取最终答案并做基本归一化。 # 优先匹配“最终答案xxx” patterns [ r最终答案[:]\s*(.), r[Aa]nswer\s*[:]\s*(.), r答案是\s*[:]?\s*(.), ] for pat in patterns: m re.search(pat, text) if m: answer m.group(1).strip().rstrip(。) return answer # 兜底取最后一个非空行 lines [line.strip() for line in text.splitlines() if line.strip()] if lines: return lines[-1].rstrip(。) return text.strip() def sample_answers(question, n_samples8, temperature0.7): 并发采样 n_samples 次返回候选答案列表。 messages [ {role: system, content: SYSTEM_PROMPT}, {role: user, content: question}, ] tasks [] with ThreadPoolExecutor(max_workersn_samples) as executor: for _ in range(n_samples): tasks.append( executor.submit(call_model, messages, temperature, True) ) sampled [] for task in tasks: resp, has_lp task.result() text get_text(resp) sampled.append({ raw_text: text, answer: extract_final_answer(text), avg_logprob: average_logprob(resp) if has_lp else None, }) return sampled这段代码里有一个容易被忽视的点并发采样时保持提交顺序这样后面分析结果时能对应到每一次调用。ThreadPoolExecutor的tasks列表保持顺序所以遍历tasks时结果顺序是稳定的。7.3 自评与约束检查def self_evaluate(question, answer): 让模型对候选答案进行一次自评返回 0-10 分。 eval_system ( 你是一个严格的正确性评委。请判断候选答案是否正确 输出 JSON格式为{\score\: 0-10, \reason\: \简短理由\} ) messages [ {role: system, content: eval_system}, { role: user, content: f题目\n{question}\n\n候选答案\n{answer}, }, ] resp, _ call_model(messages, temperature0.0, want_logprobsFalse) text get_text(resp) try: data json.loads(text) return float(data.get(score, 0.0)) except Exception: match re.search(rscore[\]?\s*[:]?\s*(\d(?:\.\d)?), text) if match: return float(match.group(1)) return 3.0 # 解析失败时给一个保守低分 def check_constraint(answer): 约束检查数学题的最终答案必须包含数字。 if answer is None: return False return bool(re.search(r\d, answer))自评的 JSON 输出格式很重要。如果模型不按 JSON 输出代码里有一个正则 fallback。如果两者都失败就返回 3.0 这个保守低分避免自评解析失败时影响整体排序。7.4 Consilience 聚合与主流程def consilience_score(freq, avg_logprob, self_score, constraint_ok): 将多条证据线加权融合为综合分。 # 频率得分达到 50% 就认为接近满分 freq_score min(freq / 0.5, 1.0) # 置信度得分对数概率越大越自信做一个简易归一化 if avg_logprob is not None: prob_score min(max(avg_logprob, -5) / 5.0, 1.0) prob_score max(prob_score, 0.0) else: prob_score None self_score_norm max(0.0, min(self_score / 10.0, 1.0)) constraint_score 1.0 if constraint_ok else 0.0 weights { freq: 0.35, prob: 0.15, self: 0.30, constraint: 0.20, } total weights[freq] * freq_score total weights[self] * self_score_norm total weights[constraint] * constraint_score if prob_score is not None: total weights[prob] * prob_score else: # 拿不到置信度时把该权重平均分给频率和自评 total (weights[prob] / 2.0) * freq_score total (weights[prob] / 2.0) * self_score_norm return total def run_verifier_free_tts(question, n_samples8, temperature0.7): 无验证器 TTS 主流程。 # 1. 基线greedy 单次结果 base_messages [ {role: system, content: SYSTEM_PROMPT}, {role: user, content: question}, ] baseline_resp, _ call_model(base_messages, temperature0.0) baseline_text get_text(baseline_resp) baseline_answer extract_final_answer(baseline_text) # 2. 多次采样 sampled sample_answers(question, n_samplesn_samples, temperaturetemperature) # 3. 按答案分组统计频率 answers [item[answer] for item in sampled] counter Counter(answers) total len(answers) # 4. 对每个高频答案计算 Consilience 分数 candidates [] for answer, count in counter.items(): freq count / total # 同类答案的平均置信度 lp_list [ item[avg_logprob] for item in sampled if item[answer] answer and item[avg_logprob] is not None ] avg_lp sum(lp_list) / len(lp_list) if lp_list else None # 自评只对高频答案做省成本 if count 2 or len(counter) n_samples // 2: self_score self_evaluate(question, answer) else: self_score 3.0 constraint_ok check_constraint(answer) score consilience_score(freq, avg_lp, self_score, constraint_ok) candidates.append({ answer: answer, count: count, freq: round(freq, 3), avg_logprob: round(avg_lp, 4) if avg_lp is not None else None, self_score: self_score, constraint_ok: constraint_ok, final_score: round(score, 4), }) candidates.sort(keylambda x: x[final_score], reverseTrue) best candidates[0] return { question: question, baseline_answer: baseline_answer, sampled_count: total, candidates: candidates, final_answer: best[answer], winner: best, } if __name__ __main__: DEMO_QUESTION ( Alice 比 Bob 的年龄大 10 岁。5 年后两人年龄之和是 40 岁。 请问 Alice 现在多少岁 ) result run_verifier_free_tts(DEMO_QUESTION, n_samples8, temperature0.7) print(问题, result[question]) print(Greedy 基线答案, result[baseline_answer]) print(最终答案, result[final_answer]) print() print(候选答案明细) for cand in result[candidates]: print(cand)这段代码有以下关键设计基线对照先输出 greedy 解码的结果再输出 TTS 的结果方便判断采样和聚合是否带来了收益。自评只对高频答案执行避免所有候选都调用自评成倍增加成本。置信度信号不可用时自动降权当模型接口不支持 logprob 时程序不会崩溃而是把缺失权重平分给频率和自评。最终输出候选明细方便排查“为什么选了这个答案”而不是只给你一个黑盒答案。8. 运行结果与效果验证运行命令export OPENAI_API_KEYyour_api_key export MODEL_NAMEgpt-4o-mini python verifier_free_tts.py如果你的模型服务不在 OpenAI 默认地址需要再设置export OPENAI_BASE_URLhttp://localhost:8000/v1输出格式类似如下实际内容取决于模型版本和采样随机性问题 Alice 比 Bob 的年龄大 10 岁。5 年后两人年龄之和是 40 岁。请问 Alice 现在多少岁 Greedy 基线答案 20 最终答案 20 候选答案明细 {answer: 20, count: 5, freq: 0.625, avg_logprob: -0.63, self_score:
返回列表