You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

预训练BERT转为nn.Sequential后调用forward提示input_ids参数不识别如何解决

报错原因
  • nn.Sequential的forward方法设计仅支持位置参数传入,不接受关键字参数,你传递input_ids=xxx、attention_mask=xxx这类关键字参数自然会触发参数不匹配的报错。
  • 你调用list(model_d.modules())[:-6]的逻辑本身存在严重错误:nn.Module.modules()方法会递归返回所有子模块,第一个返回的元素是model_d本身,后续会依次返回model_d.bert、model_d.bert.embeddings、model_d.bert.encoder等所有嵌套子模块,直接切片拿到的模块序列完全不是你想要的“倒数第6层及之前的BERT结构”,就算解决了参数问题也拿不到正确输出。
解决方法

推荐直接基于HuggingFace BERT原生的隐藏层输出能力自定义封装模型,不要硬拆模块,也不要用不适合多输入场景的nn.Sequential,实现代码如下:
自定义截断BERT类:

import torch
import torch.nn as nn

class TruncatedBERT(nn.Module):
    def __init__(self, original_model):
        super().__init__()
        # 直接复用原模型的BERT主干和Dropout层
        self.bert = original_model.bert
        self.dropout = original_model.drop

    def forward(self, input_ids, attention_mask):
        # 开启所有隐藏层输出
        bert_outputs = self.bert(
            input_ids=input_ids,
            attention_mask=attention_mask,
            output_hidden_states=True
        )
        # hidden_states为从embedding到顶层encoder的所有输出,负索引直接取倒数第6层
        target_output = bert_outputs.hidden_states[-6]
        # 可选择保留原有的Dropout逻辑,不需要可删除
        target_output = self.dropout(target_output)
        return target_output

实例化和调用代码:

# 加载原模型
model_d = torch.load(f'{conf.save_path}/DeepPavlov/rubert-base-cased_2.pt', map_location=device)
# 实例化截断后的BERT模型
newmodel_bert = TruncatedBERT(model_d)
# 调用方式和原模型完全一致
output = newmodel_bert(
    input_ids = next(iter(train_data_loader))['input_ids'],
    attention_mask = next(iter(train_data_loader))['attention_mask']
)

如果需要冻结BERT主干参数不参与训练,可以在实例化后添加:

for param in newmodel_bert.bert.parameters():
    param.requires_grad = False

内容的提问来源于stack exchange,提问作者BIG_BIT

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.02 23:24:03