
Mistral 等基于 Transformer 的 LLM 其 embed_tokens 层仅接受 torch.Tensor 类型的 token ID 张量作为输入,而非原始 Python 列表或 Hugging Face 的 BatchEncoding 对象;正确做法是调用 tokenizer 时显式指定 return_tensors='pt'。
mistral 等基于 transformer 的 llm 其 `embed_tokens` 层仅接受 `torch.tensor` 类型的 token id 张量作为输入,而非原始 python 列表或 hugging face 的 `batchencoding` 对象;正确做法是调用 tokenizer 时显式指定 `return_tensors='pt'`。
在微调或特征提取任务中,常需直接访问 Mistral 模型的词嵌入层(即 model.model.embed_tokens),该层本质是一个 torch.nn.Embedding(vocab_size, hidden_size) 模块(例如 Embedding(32000, 4096))。但其输入有严格类型要求:必须是形状为 (batch_size, seq_len) 的 torch.LongTensor,且元素为有效词汇表索引(token IDs)。
若直接传入 tokenizer("Hello world"),返回的是 BatchEncoding 字典对象(含 input_ids, attention_mask 等字段),不满足 Embedding.forward() 的签名,会报错:
TypeError: embedding(): argument 'indices' (position 2) must be Tensor, not BatchEncoding
而传入 tokenizer(...).input_ids 得到的是 Python list(如 [1, 872, 5793, 2]),同样被拒绝:
TypeError: embedding(): argument 'indices' (position 2) must be Tensor, not list
✅ 正确解法:在 tokenizer 调用时启用 return_tensors='pt' 参数,让其原生返回 PyTorch 张量:
# ✅ 推荐:一步到位,返回 torch.Tensor
inputs = tokenizer("Hello world", return_tensors="pt")
embedded = model.model.embed_tokens(inputs.input_ids) # shape: [1, seq_len, hidden_size]
print(f"Input IDs shape: {inputs.input_ids.shape}") # e.g., torch.Size([1, 4])
print(f"Embedding shape: {embedded.shape}") # e.g., torch.Size([1, 4, 4096])
⚠️ 注意事项:
- return_tensors='pt' 是 tokenizer 的标准参数,无需额外配置,但必须显式声明(默认为 None,返回 Python list);
- 若处理批量文本,可直接传入字符串列表:tokenizer(["Hello", "world"], return_tensors="pt"),自动 padding 并返回二维张量;
- 确保 input_ids 设备与模型一致(如 CUDA):inputs = inputs.to(model.device)(尤其在多卡/混合精度场景下);
- embed_tokens 输出为 bfloat16(因模型以 torch.bfloat16 加载),如需 float32 可后接 .float(),但注意显存与精度权衡。
? 进阶提示:若需兼容训练流程(如 SFTTrainer),建议统一使用 DataCollatorForLanguageModeling 或自定义 collator,确保 input_ids 始终以 torch.Tensor 形式进入 forward(),避免运行时类型转换开销。
总之,return_tensors='pt' 是连接 tokenizer 与 embedding 层的关键桥梁——它不仅是语法糖,更是保证数据流类型安全、性能可控的必要实践。










