微调microsoft/DialoGPT-medium遇ValueError:模型未返回损失值
解决DialoGPT-medium微调时未返回loss的问题
报错信息
ValueError: The model did not return a loss from the inputs, only the following keys: logits,past_key_values. For reference, the inputs it received are input_ids,attention_mask.
问题原因
AutoModelForCausalLM(DialoGPT基于该类实现)必须传入labels参数才会自动计算损失。因果语言模型的训练逻辑是用输入序列预测下一个token,需要以输入序列作为标签(模型内部会自动偏移处理),但你的数据集仅包含input_ids和attention_mask,缺少labels字段,导致模型无法生成loss。
解决方案
修改数据处理逻辑,在tokenize阶段添加labels字段,并将padding位置的label设为-100(PyTorch会自动忽略-100对应的损失计算)。
修改后的完整代码
from datasets import Dataset from transformers import Trainer, TrainingArguments, default_data_collator, AutoModelForCausalLM, AutoTokenizer dataset = Dataset.load_from_disk('dataset') print(dataset.column_names) model = AutoModelForCausalLM.from_pretrained('microsoft/DialoGPT-medium') tokenizer = AutoTokenizer.from_pretrained('microsoft/DialoGPT-medium') tokenizer.pad_token = tokenizer.eos_token def tokenize_function(examples): tokenized_inputs = tokenizer( examples["prompt"], truncation=True, padding=True, max_length=512 ) # 添加labels字段,与input_ids内容一致 tokenized_inputs["labels"] = tokenized_inputs["input_ids"].copy() # 将pad_token对应的label设为-100,排除padding部分的损失计算 if tokenizer.pad_token_id is not None: tokenized_inputs["labels"] = [ [-100 if token == tokenizer.pad_token_id else label for token, label in zip(input_ids, labels)] for input_ids, labels in zip(tokenized_inputs["input_ids"], tokenized_inputs["labels"]) ] return tokenized_inputs tokenized_datasets = dataset.map(tokenize_function, batched=True) tokenized_datasets = tokenized_datasets.remove_columns("prompt") training_args = TrainingArguments( output_dir="./model", # 输出目录 overwrite_output_dir=True, # 覆盖输出目录内容 num_train_epochs=3, # 训练轮数 per_device_train_batch_size=32, # 训练批次大小 per_device_eval_batch_size=64, # 评估批次大小 eval_steps=400, # 两次评估之间的更新步数 save_steps=800, # 保存模型的步数间隔 warmup_steps=500, # 学习率调度器的预热步数 remove_unused_columns=False, ) trainer = Trainer( model=model, args=training_args, data_collator=default_data_collator, train_dataset=tokenized_datasets, ) trainer.train() trainer.save_model()
关键修改点
- 在
tokenize_function中新增labels字段,值为input_ids的副本 - 遍历labels列表,将所有pad_token对应的位置设为
-100,避免计算padding部分的无效损失
内容的提问来源于stack exchange,提问作者Alfie Barlow
相关产品推荐
相关产品推荐

