添加自定义词后BertTokenizer触发PanicException异常求助
解决PanicException: AddedVocabulary bad split问题
问题背景
使用BertTokenizer通过add_tokens()添加大量自定义词后,训练BartForConditionalGeneration模型过程无异常,但用pipeline调用上传到Hub的模型时,频繁触发PanicException: AddedVocabulary bad split异常。
解决方案
1. 手动加载训练后的自定义Tokenizer
pipeline默认会自动加载模型关联的原始Tokenizer,不会包含你新增的自定义词,导致词汇表不匹配引发异常。必须手动加载上传到Hub的Tokenizer,并在初始化pipeline时指定:
text = "Words to translate" from transformers import pipeline, BertTokenizer hf_model_name = "my_huggingface_username/" + output_model # 加载训练后上传的Tokenizer tokenizer = BertTokenizer.from_pretrained(hf_model_name) # 指定tokenizer初始化pipeline translator = pipeline("translation", model=hf_model_name, tokenizer=tokenizer, max_length=200) print(translator(text)[0]['translation_text'].replace(' ', ''))
2. 确保模型嵌入层适配新增词汇
添加自定义词后,必须手动扩容模型的嵌入层,否则模型词汇表大小与Tokenizer不匹配,会在推理时触发异常。修改训练代码中的模型初始化步骤:
checkpoint = 'fnlp/bart-base-chinese' tokenizer = BertTokenizer.from_pretrained(checkpoint) # 添加自定义词,记录新增数量 num_added_tokens = tokenizer.add_tokens(["Token1", "Token2"]) # 实际为百万级自定义词 model = BartForConditionalGeneration.from_pretrained(checkpoint, output_attentions=True, output_hidden_states=True) # 扩容模型嵌入层,适配新增词汇 if num_added_tokens > 0: model.resize_token_embeddings(len(tokenizer)) # 确保Bart的decoder嵌入层与共享嵌入层同步 model.model.decoder.embed_tokens = model.model.shared
3. 检查自定义词汇的格式
如果自定义词包含空格、特殊分隔符等字符,会导致Tokenizer拆分逻辑出错。确保所有新增自定义词为连续无分隔符的字符串,避免添加类似"Token 1"带空格的词汇。
4. 验证Hub仓库文件完整性
训练后push_to_hub时,确认以下Tokenizer相关文件已上传到Hub模型仓库:
vocab.txtadded_tokens.jsontokenizer_config.json
检查added_tokens.json是否包含所有你添加的自定义词,确保文件未损坏或缺失。
内容的提问来源于stack exchange,提问作者Raptor
相关产品推荐
相关产品推荐

