Diffusers Textual Inversion 加载指南:TextualInversionLoaderMixin 原理与实战
2026/9/10 20:27:05 网站建设 项目流程

Diffusers Textual Inversion 加载指南:TextualInversionLoaderMixin 原理与实战

【免费下载链接】diffusers🤗 Diffusers: State-of-the-art diffusion models for image, video, and audio generation in PyTorch.项目地址: https://gitcode.com/GitHub_Trending/di/diffusers

Textual Inversion(文本反演)是一种仅凭 3~5 张示例图片即可个性化扩散模型概念(如某个物体、某种画风)的训练方法,其产物是极小的词嵌入文件(仅几 KB),可随后加载进文本编码器使用。本文围绕TextualInversionLoaderMixin展开,讲解在 Diffusers 中加载 Diffusers 格式与 Automatic1111 格式嵌入的完整流程、底层实现原理,并覆盖多向量嵌入、负向嵌入与卸载等进阶用法。

什么是 Textual Inversion

Textual Inversion 通过微调模型的**词嵌入(word embeddings)**来学习新概念:把 3~5 张示例图片与一个特殊 token(如<sks>)绑定,训练后该 token 的嵌入向量便"记住"了概念。由于只更新嵌入向量而不动 UNet/VAE,训练产物通常只有几 KB,扩散模型本身仍以原始方式使用。

正因为权重极小,嵌入必须在用DiffusionPipeline.from_pretrained加载完模型之后再加载。Diffusers 通过TextualInversionLoaderMixin提供统一入口:既能加载 Diffusers 官方格式的嵌入,也能加载 Automatic1111(WebUI)生态生成的.pt嵌入文件,并把对应 token 注册进 tokenizer。

加载嵌入的完整流程

准备 pipeline

先加载基础 pipeline,再挂载嵌入:

import torch from diffusers import AutoPipelineForText2Image pipeline = AutoPipelineForText2Image.from_pretrained( "stable-diffusion-v1-5/stable-diffusion-v1-5", dtype=torch.float16 ).to("cuda") # 或 "mps"、"xpu"、"cpu"

加载 Diffusers 格式嵌入

pipeline.load_textual_inversion("sd-concepts-library/gta5-artwork") prompt = "A cute brown bear eating a slice of pizza, stunning color scheme, masterpiece, illustration, <gta5-artwork> style" pipeline(prompt).images[0]

加载后,只需在 prompt 中写入嵌入对应的特殊 token(如<gta5-artwork>),即可激活该概念。

加载 Automatic1111 格式嵌入

Automatic1111 格式的嵌入是.pt文件(可从 CivitAI 等站点下载),加载时通常需要显式指定token

from diffusers import StableDiffusionPipeline import torch model_id = "stable-diffusion-v1-5/stable-diffusion-v1-5" pipe = StableDiffusionPipeline.from_pretrained(model_id, torch_dtype=torch.float16).to("cuda") pipe.load_textual_inversion("./charturnerv2.pt", token="charturnerv2") prompt = "charturnerv2, multiple views of the same character in the same outfit, a character turnaround of a woman wearing a black jacket and red shirt, best quality, intricate details." image = pipe(prompt, num_inference_steps=50).images[0] image.save("character.png")

源码通过_retrieve_tokens_and_embeddings自动识别两种格式:Diffusers 格式的 state dict 只有单个键(token→embedding);A1111 格式则包含string_to_param键与name键(见 textual_inversion.py)。

自定义权重文件名

若嵌入文件以自定义名称保存,用weight_name指定:

pipeline.load_textual_inversion( "EvilEngine/easynegative", weight_name="easynegative.safetensors", token="easynegative" )

负向嵌入:用 Textual Inversion 提升画质

Textual Inversion 也可训练负向嵌入(negative embeddings),引导模型远离"模糊""丑陋"等不良特征。EasyNegative 是广泛使用的多概念负向嵌入。加载后把对应 token 传给negative_prompt即可生效:

import torch from diffusers import AutoPipelineForText2Image pipeline = AutoPipelineForText2Image.from_pretrained( "stable-diffusion-v1-5/stable-diffusion-v1-5", dtype=torch.float16 ).to("cuda") # 或 "mps"、"xpu"、"cpu" pipeline.load_textual_inversion( "EvilEngine/easynegative", weight_name="easynegative.safetensors", token="easynegative" ) prompt = "A cute brown bear eating a slice of pizza, stunning color scheme, masterpiece, illustration" negative_prompt = "easynegative" pipeline(prompt, negative_prompt).images[0]

参数详解

load_textual_inversion支持多种输入与选项,关键参数如下(完整签名见 textual_inversion.py):

参数类型说明
pretrained_model_name_or_pathstr/PathLike/Dict或它们的 listHub 上的模型 ID(如sd-concepts-library/low-poly-hd-logos-icons)、本地目录(./my_text_inversion_directory/)、本地文件(./my_text_inversions.pt)或 torch state dict
tokenstr/list[str],可选覆盖嵌入自带的 token;当传入 list 时长度须与模型 list 一致
tokenizerCLIPTokenizer,可选缺省使用self.tokenizer
text_encoderCLIPTextModel,可选缺省使用self.text_encoder
weight_namestr,可选自定义权重文件名,适用于 Diffusers 格式改名保存或 A1111 格式
cache_dirstr/PathLike,可选模型下载缓存目录
force_downloadbool,默认False是否强制重新下载权重
proxiesdict[str, str],可选按协议/端点配置代理,如{'http': 'foo.bar:3128'}
local_files_onlybool,默认FalseTrue时只加载本地权重,不从 Hub 下载
hf_tokenstr/bool,可选Hub 鉴权 token;为True时使用diffusers-cli login生成的 token
revisionstr,默认"main"指定模型版本(分支名、标签名或 commit id)
subfolderstr,默认""模型仓库内的子目录位置
mirrorstr,可选国内下载镜像源

源码原理:加载过程拆解

load_textual_inversion的执行可拆解为以下步骤:

  1. 归一化输入:将pretrained_model_name_or_pathtoken包装为 list,若未提供 token 则按模型数量复制None(L379-L387)。
  2. 校验输入_check_text_inv_inputs检查 tokenizer/text_encoder 是否缺失、list 长度是否匹配、token 是否重复(L180-L201)。
  3. 加载 state dictload_textual_inversion_state_dicts优先尝试.safetensorslearned_embeds.safetensors),失败后回退到 pickle 格式(learned_embeds.bin),两个常量定义于 textual_inversion.py。
  4. 解析 token 与嵌入_retrieve_tokens_and_embeddings区分 torch.Tensor、单键 diffusers 格式、含string_to_param的 A1111 格式三种情况;若用户传入的 token 与文件内 token 不同,会以传入的为准并打印日志(L229-L232)。
  5. 处理多向量嵌入_extend_tokens_and_embeddings将形状为(N, dim)的多向量嵌入拆成token, token_1, ..., token_{N-1}多个单向量 token(L244-L269)。
  6. 维度校验:每个嵌入的最后一维必须等于text_encoder.get_input_embeddings().weight.shape[-1],否则报错(L412-L417)。
  7. 注入文本编码器:先处理 CPU offload hook(若之前启用过 model/sequential offload,先移除再重挂),再调用resize_token_embeddings(len(tokenizer) + len(tokens))扩展嵌入矩阵,最后tokenizer.add_tokens(token)+input_embeddings.data[token_id] = embedding写入新向量(L420-L465)。

多向量 token 的 prompt 展开

多向量嵌入的 token 在 prompt 中如何生效?maybe_convert_prompt(L123-L178)负责把 prompt 里的单一 token 展开为token token_1 token_2 ...序列。这一逻辑被 SD、SDXL、Flux、AnimateDiff 等众多 pipeline 在编码 prompt 前调用,例如 pipeline_animatediff.py 与 encoders.py。

多嵌入批量加载与显式 tokenizer/text_encoder

load_textual_inversion支持一次加载多个嵌入(pretrained_model_name_or_path传 list 时token也须等长),并可显式指定 tokenizer 与 text_encoder。典型场景是 SDXL:它的两个文本编码器需要分别加载嵌入。

pipeline = AutoPipelineForText2Image.from_pretrained("stabilityai/stable-diffusion-xl-base-1.0") embedding_path = hf_hub_download(repo_id="linoyts/web_y2k", filename="web_y2k_emb.safetensors", repo_type="model") state_dict = load_file(embedding_path) # 加载到 text_encoder 1(CLIP ViT-L/14) pipeline.load_textual_inversion( state_dict["clip_l"], tokens=["<s0>", "<s1>"], text_encoder=pipeline.text_encoder, tokenizer=pipeline.tokenizer, ) # 加载到 text_encoder 2(CLIP ViT-G/14) pipeline.load_textual_inversion( state_dict["clip_g"], tokens=["<s0>", "<s1>"], text_encoder=pipeline.text_encoder_2, tokenizer=pipeline.tokenizer_2, )

卸载嵌入

unload_textual_inversion(L467-L605)支持移除全部或指定的嵌入:

from diffusers import AutoPipelineForText2Image pipeline = AutoPipelineForText2Image.from_pretrained("stable-diffusion-v1-5/stable-diffusion-v1-5") # 示例 1:移除所有 token 嵌入 pipeline.load_textual_inversion("sd-concepts-library/gta5-artwork") pipeline.load_textual_inversion("sd-concepts-library/moeb-style") pipeline.unload_textual_inversion() # 示例 2:只移除一个 token pipeline.load_textual_inversion("sd-concepts-library/moeb-style") pipeline.load_textual_inversion("sd-concepts-library/gta5-artwork") pipeline.unload_textual_inversion("<moe-bius>") # 示例 3:SDXL 上按编码器分别卸载 pipeline = AutoPipelineForText2Image.from_pretrained("stabilityai/stable-diffusion-xl-base-1.0") # ... 先按上文方式分别加载到两个编码器 ... pipeline.unload_textual_inversion( tokens=["<s0>", "<s1>"], text_encoder=pipeline.text_encoder, tokenizer=pipeline.tokenizer ) pipeline.unload_textual_inversion( tokens=["<s0>", "<s1>"], text_encoder=pipeline.text_encoder_2, tokenizer=pipeline.tokenizer_2 )

卸载时只清理"非特殊"的 added token(保留[UNK][EOS]等真正的特殊 token),并从文本编码器的嵌入矩阵中删除对应行、重建nn.Embedding(L592-L605)。Fast 与 Slow tokenizer 走两条不同的内部清理路径(L558-L590)。

测试验证:多格式与 CPU offload 兼容性

仓库测试 test_stable_diffusion.py 提供了三个关键用例:

  • test_stable_diffusion_textual_inversion:同时加载 Hub 上的 Diffusers 格式嵌入(low-poly-hd-logos-icons)与两个 A1111 格式文件(winter_style.ptwinter_style_negative.pt),并断言生成结果与基准 numpy 数据的最大差异小于阈值;
  • test_stable_diffusion_textual_inversion_with_model_cpu_offload:验证启用enable_model_cpu_offload后加载嵌入仍正常——这正是源码中"先移除 hook、加载、再恢复 hook"逻辑(L422-L463)的回归保护;
  • test_stable_diffusion_textual_inversion_with_sequential_cpu_offload:同上,覆盖enable_sequential_cpu_offload场景。

训练侧补充:嵌入从何而来

加载是消费端,训练是生产端。Diffusers 提供完整的训练脚本 textual_inversion.py,核心训练参数包括:

  • --pretrained_model_name_or_path:Hub 模型名或本地路径;
  • --train_data_dir:训练图片目录;
  • --placeholder_token:学习到的嵌入所绑定的特殊词(推理时必须写在 prompt 中);
  • --initializer_token:粗略描述训练对象的初始化词;
  • --learnable_propertystyle(风格,如梵高画风)或object(物体,如你的狗);
  • --num_vectors:学习嵌入所用的向量数,越大效果越好但训练成本越高;
  • --checkpointing_steps:保存检查点的频率,配合--resume_from_checkpoint可断点续训。

训练细节可参考 训练指南,其中还建议在显存受限时开启gradient_checkpointingmixed_precision。训练产出的嵌入即可用本文的方法加载使用。

总结

  • Textual Inversion 只训练词嵌入,产物仅几 KB,须在from_pretrained之后通过load_textual_inversion加载;
  • 同时兼容 Diffusers(learned_embeds.safetensors/.bin)与 Automatic1111(.pt)两种格式,A1111 格式通常需显式传token
  • 支持多向量嵌入(自动展开为token token_1 ...)、负向嵌入(配合negative_prompt)、批量加载与按编码器精确卸载;
  • 与 model/sequential CPU offload 兼容,仓库测试给出了完整的回归验证;
  • 训练侧脚本与参数可参考 textual_inversion.py 与 训练文档。

【免费下载链接】diffusers🤗 Diffusers: State-of-the-art diffusion models for image, video, and audio generation in PyTorch.项目地址: https://gitcode.com/GitHub_Trending/di/diffusers

创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询