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

GPT-Neo微调文本分类遇AttributeError报错求助

GPT-Neo微调tweet_eval情感分类报错排查:AttributeError: 'list' object has no attribute 'keys'

问题背景

使用Hugging Face的tweet_eval情感子集,基于GPT-Neo-2.7B做文本分类,运行trainer.train()时触发AttributeError: 'list' object has no attribute 'keys'错误。

错误原因

核心问题是传给Trainer的数据集格式错误:

  • 手动拆分了数据集的文本和标签,用tokenizer批量处理后得到的train_inputs是一个包含input_ids、attention_mask等键的大字典(每个键对应所有样本的列表),但Trainer需要的是每个元素为单样本字典的数据集结构(比如Hugging Face Dataset对象,或[{"input_ids": [...], "attention_mask": [...], "label": ...}, ...]形式的列表)。
  • 当DataLoader尝试迭代这个大字典时,会把每个键对应的值(比如input_ids的列表)当成单个样本,导致后续pad函数接收到列表而非字典,触发keys属性不存在的错误。

修正后的完整代码

from transformers import AutoModelForSequenceClassification, AutoTokenizer, TrainingArguments, Trainer
import datasets
import torch as t
from transformers import DataCollatorWithPadding
import evaluate
import numpy as np

# 直接加载数据集,不手动拆分文本和标签
dataset = datasets.load_dataset("tweet_eval", "emotion")

def load_LLM(llm, device):
    num_labels = 4
    id2label = {0: "Anger", 1: "Joy", 2: "Optimism", 3: "Sadness"}
    label2id = {"Anger": 0, "Joy": 1, "Optimism": 2, "Sadness":3}
    model = AutoModelForSequenceClassification.from_pretrained(llm, num_labels=num_labels, id2label=id2label, label2id=label2id)
    model.to(device)
    tokenizer = AutoTokenizer.from_pretrained(llm)
    return model, tokenizer

llm = "EleutherAI/gpt-neo-2.7B"
device = t.device('cuda' if t.cuda.is_available() else 'cpu')
model, tokenizer = load_LLM(llm, device)

# GPT-Neo默认无pad token,推荐用eos_token替代,避免新增特殊token导致embedding不匹配
tokenizer.pad_token = tokenizer.eos_token

# 定义tokenization函数,在原始数据集上批量处理
def tokenize_function(examples):
    return tokenizer(examples["text"], truncation=True)

# 对数据集做tokenization,保留label字段
tokenized_datasets = dataset.map(tokenize_function, batched=True)

data_collator = DataCollatorWithPadding(tokenizer=tokenizer)

accuracy = evaluate.load("accuracy")
def compute_metrics(eval_pred):
    predictions, labels = eval_pred
    predictions = np.argmax(predictions, axis=1)
    return accuracy.compute(predictions=predictions, references=labels)

training_args = TrainingArguments(
    output_dir="my_awesome_model",
    learning_rate=2e-5,
    per_device_train_batch_size=16,
    per_device_eval_batch_size=16,
    num_train_epochs=2,
    weight_decay=0.01,
    evaluation_strategy="epoch",
    save_strategy="epoch",
    load_best_model_at_end=True,
    push_to_hub=True,
    # GPT-Neo-2.7B参数量大,显存不足时开启梯度检查点
    gradient_checkpointing=True
)

trainer = Trainer(
    model=model,
    args=training_args,
    train_dataset=tokenized_datasets["train"],
    eval_dataset=tokenized_datasets["test"],
    tokenizer=tokenizer,
    data_collator=data_collator,
    compute_metrics=compute_metrics
)

trainer.train()

关键修改说明

  1. 保留Dataset原始结构:不再手动拆分文本和标签,用dataset.map()批量处理tokenization,确保每个样本保留label字段,生成符合要求的Dataset对象。
  2. 正确设置pad token:用GPT-Neo自带的eos_token作为pad token,避免新增特殊token导致模型embedding层不兼容。
  3. 传递合规数据集:将处理后的tokenized_datasets["train"]和tokenized_datasets["test"]传给Trainer,而非tokenizer返回的大字典。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.19 00:37:55