从 gliner_medium_news 到 2.5-multi:GLiNER 三代架构进化,每一步改了啥
【免费下载链接】gliner2.5-multi-v1项目地址: https://ai.gitcode.com/hf_mirrors/fastino/gliner2.5-multi-v1
命名实体识别(NER)领域在过去两年经历了一场静默的架构革命:从"每个任务训一个专用模型",到"一个轻量模型零样本抽任意实体",再到"一个模型同时抽实体、分文本、抽关系、建结构化记录"。GLiNER 这条技术线正好完整走过了这三个阶段——从社区广泛使用的gliner_medium_news-v2.1,到主打边缘部署的 60M 参数 bi-encoder 版本,再到本仓库gliner2.5-multi-v1这样的多语言多任务合流模型。
很多人只把 GLiNER 当作"又一个 NER 工具",却忽略了它三代架构之间本质性的取舍变化:跨度表示从"密集宽度网格"到"标签预计算"再到"稀疏边界配对"。本文不堆概念,而是沿着"每一步改了啥"这条线,用论文数据与仓库真实配置,把三代架构的动机、改动与代价拆开讲清楚。
第一代:uni-encoder 与 v2.1 的 18 基准 +7.5%
GLiNER 的核心思路(原论文 arXiv 2311.08526)非常直接:把实体类型当作"提示词"拼进输入,而不是当作固定标签表。输入被构造成[P] entities ([E] person [E] location) [SEP] 原文文本,模型对文本中所有可能的跨度(span)与每个实体类型嵌入计算匹配分数,分数超过阈值即判定为实体。这套被后来论文称为uni-encoder的方案,最大的优势是零样本:实体类型在推理时才以自然语言形式给出,模型从没见过也能识别。
gliner_medium_news-v2.1正是这一代的典型产物——在 GLiNER 原始架构上针对新闻长文本场景微调得到。社区公开评测中,它最被反复引用的一组数字是:在 18 个基准数据集上,零样本准确度平均提升 7.5%。这 7.5% 从哪来?拆开看有三层来源:
- 合成数据扩容:GLiNER 系列的训练数据大量由 LLM 自动标注生成(pseudo-labeling + 合成文本),v2.1 在此基础上补充了新闻领域的合成样本,让模型在"谁、何时、何地、何组织"这类新闻高频实体上的覆盖更密集;
- 负样本工程:v2.1 之后的训练管线显著强化了难负样本策略(hard negatives),模型学会了"不像实体的跨度"长什么样,而不是盲目给高置信度;
- 长文本适应:新闻正文动辄上千 token,v2.1 针对长序列做了专门的截断与跨度窗口适配。
但这一代的天花板也很明显:跨度表示依赖固定宽度的网格,模型要为每个可能的"起点-终点对"枚举候选,宽度一旦超过训练时见过的最大值就无能为力;同时文本和标签共享同一个编码器,标签数量超过约 50 个时,性能会明显衰减。
第二代:60M 边缘版与 bi-encoder 的路线选择
如果说第一代解决的是"能不能零样本",第二代GLiNER v2解决的是"能不能跑在边缘设备上"。社区对其的总结相当直白:6000 万参数、在 60 亿高质量 token 上训练、专为边缘设备优化。
它做了两个关键路线选择:
其一,架构上从 uni-encoder 切换到 bi-encoder。文本与标签不再拼进同一个编码器,而是分别编码:文本走一遍编码器,标签嵌入可以预先计算并缓存。推理时,一次文本前向 + 一组标签点积即可完成对所有候选标签的打分。这种解耦带来两个直接收益:一是标签规模不再受编码窗口限制,可以扩展到数百乃至上千个实体类型;二是省掉了"每个标签都要参与注意力计算"的开销——官方宣称相对逐标签推理可实现约130 倍加速,这基本是边缘场景从"不可用"到"可用"的分界线。
其二,数据策略上强调"数据密度优于参数规模"。60M 参数的模型敢打零样本,靠的是 60 亿 token 的高质量、跨领域训练数据(法律、金融、科学等),而不是盲目堆参数。这也奠定了 GLiNER 家族后续所有版本的训练哲学:用数据广度换参数深度,用架构效率换算力。
但 bi-encoder 也有代价:文本与标签分家后,跨度与标签之间的交互建模变浅,对需要强上下文约束的细粒度实体(如"既可以是人名也可以是地名的专名消歧")不如 uni-encoder 细腻。这为第三代架构的回归埋下了伏笔。
第三代:2.5-multi-v1 的多语言 + 多任务合流
第二代解决了规模与速度,但信息抽取的终极形态不是"更快地抽实体",而是"一次前向,抽完所有想要的结构"。GLiNER2(论文 arXiv 2507.18546)正是这条合流路线的产物,而本仓库的gliner2.5-multi-v1是这条路线上的多语言边界检查点(boundary checkpoint)。
边界架构:用稀疏配对替代宽度网格
打开仓库的 config.json,第一行就是答案:"architecture": "boundary",对应的实现类是BoundaryExtractor。与第一代"枚举所有可能跨度的密集网格"不同,boundary 架构把任务拆成两步:
- 先分别预测"起点候选"和"终点候选":配置里
start_top_k: 24、end_top_k: 24、candidate_budget: 192、ends_per_start: 12这些参数表明,模型先各自选出 Top-K 的起点与终点 token,再做稀疏的起点-终点配对,而不是在[L, W]的密集宽度网格上打分; - 配对分数决定跨度是否成立:
pool_size: 192与candidate_pool: "shared"说明候选跨度的池化是共享的,配合use_inside_evidence: true、query_conditioned_inside_weight: true让跨度内部证据参与判定。
这一改动的直接收益写在 README 的 Model details 里:任何能塞进编码窗口的长度都可以表示(max_len: 4096),不再受训练时见过的最大跨度宽度限制;同时因为只配对 Top-K 候选而非全枚举,计算量不随文本长度平方级爆炸。README 特别警告:GLiNER2.from_pretrained(...)是旧的 span 加载器,"will not dispatch this checkpoint"——两种架构在推理层面已经彻底分家。
多语言:mDeBERTa-v3 打底
多语言版选择了microsoft/mdeberta-v3-base作为编码器(见 config.json 的"model_name"字段)。从 encoder_config/config.json 可以看到它的底子:12 层、hidden size 768、250,112 词表、512 的 max_position_embeddings,dtype 为 fp16。287M 总参数(README 家族表)换来的是跨语种的统一抽取能力,模型卡片明确标注为 multilingual,pipeline 为 token-classification 并覆盖 Text classification / Relation Extraction / Structured extraction 等 tag。
多任务合流:一个 schema,一次前向
第三代真正的"合流"体现在任务层面。README 中 GLiNER2.5 家族定位很清晰:
| 检查点 | 参数量 | 编码器 | 语言 | 定位 |
|---|---|---|---|---|
| gliner2.5-small-v1 | 74M | DeBERTa-v3-xsmall | 英文 | 快速 CPU 抽取/分类 |
| gliner2.5-base-v1 | 194M | DeBERTa-v3-base | 英文 | 英文多任务默认 |
| gliner2.5-multi-v1 | 287M | mDeBERTa-v3-base | 多语言 | 多语言多任务默认 |
gliner2.5-multi-v1在 config.json 里明确开启了三个任务头:enable_records: true、enable_relations: true、enable_count_head: true(count head 是结构化记录中"预测实例数量 K"的机制),外加enable_abstention: true让模型有权对不确定的标签"弃权"。分类、记录、关系、跨度属性(span attributes)全部挂在同一个 boundary head 下,通过 schema 接口组合:
schema = ( model.create_schema() .entities({ "person": "Named people", "organization": "Companies or teams", "product": "Named products or services", }) .entity_attributes({ "sentiment": AttributeGroup( ["positive", "negative", "neutral"], applies_to=["person"], qualify_labels=True, ) }) .classification("topic", ["technology", "business", "sports", "politics"]) .relations(["works_for", "announced"]) .structure("announcement", mode="natural", anchor="product") .field("company", dtype="str") .field("product", dtype="str", cardinality="required_one") )对"Apple CEO Tim Cook unveiled the iPhone 15 Pro for $999."一次extract,返回的不仅有person / organization / product三类实体,还有文档级topic、每条person的独立sentiment、works_for/announced关系边、以及按实例对齐的announcement结构化记录。这在第一代是不可想象的——v2.1 时代这需要 NER 模型 + 分类模型 + 关系模型三套部署。
值得注意的是,多任务合流是有代价的:GLiNER2 论文在 CrossNER 基准上整体 F1 为 0.590,与专攻 NER 的 GLiNER-M(0.615)和 GPT-4o(0.599)相比略有下降,但换来的是单模型覆盖 NER、分类、结构化抽取三类任务,且 CPU 上 20 标签分类延迟仅 163ms(对比 DeBERTa 逐标签推理 6758ms、GPT-4o 425ms)。以少量 NER 精度换 2~3 个数量级的部署成本下降,这是"合流"路线的核心交易。
三代对比:一张表看透演进逻辑
| 维度 | 第一代(v2.1 / uni-encoder) | 第二代(v2 bi-encoder) | 第三代(2.5-multi / boundary) |
|---|---|---|---|
| 跨度建模 | 密集[L, W]宽度网格 | 标签预计算 + 点积打分 | 稀疏 start/end 配对,任意跨度 |
| 标签规模 | ~50 个类型上限 | 数百~上千类型 | 通过 schema 组合,无硬上限 |
| 推理加速 | 逐标签前向 | 一次文本编码 + 缓存标签 | 一次前向多任务联合 |
| 任务范围 | 仅 NER | NER + 部分分类 | NER + 分类 + 记录 + 关系 + 属性 |
| 语言 | 单语为主 | 多语 PII 等 | mDeBERTa-v3 多语合流 |
| 代表证据 | 18 基准 +7.5% | 130× 加速、60 亿 token | max_len 4096、287M、schema 接口 |
回看这三步,进化的主线始终是同一个问题:在"模型够小、CPU 可跑"的约束下,如何把信息抽取的覆盖面做到最大。第一代用提示词换来了零样本,第二代用标签解耦换来了规模与速度,第三代用边界配对 + 多任务头换来了"一次前向覆盖全部抽取需求"。gliner2.5-multi-v1正是这条演进线的当前终点:架构上是最新的 boundary extractor,语言上是多语,任务上是 NER/分类/记录/关系/属性五合一——它不是又一个 NER 模型,而是把整个信息抽取管线压缩进了单个 287M 参数检查点里的一次前向。
【免费下载链接】gliner2.5-multi-v1项目地址: https://ai.gitcode.com/hf_mirrors/fastino/gliner2.5-multi-v1
创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考