做卖蜂蜜的网站计划书,重庆网站关键词推广,海外网络推广效果,河南建设Stable Diffusion XL on diffusers 翻译自#xff1a;https://huggingface.co/docs/diffusers/using-diffusers/sdxl v0.24.0 非逐字翻译 Stable Diffusion XL (SDXL) 是一个强大的图像生成模型#xff0c;其在上一代 Stable Diffusion 的基础上主要做了如下优化#xff1a;…Stable Diffusion XL on diffusers 翻译自https://huggingface.co/docs/diffusers/using-diffusers/sdxl v0.24.0 非逐字翻译 Stable Diffusion XL (SDXL) 是一个强大的图像生成模型其在上一代 Stable Diffusion 的基础上主要做了如下优化
参数量增加SDXL 中 Unet 的参数量比前一代大了 3 倍并且 SDXL 还引入了第二个 text-encoderOpenCLIP ViT-bigG/14整体参数量大幅增加。引入了 size-conditioning 和 crop conditioning在训练阶段有效利用起低分辨率图像并在推理对生成的图片是否需要裁剪有更好的控制。使用了两阶段的生成过程除了第一阶段的 base 模型生成之外还加入了一个 refiner 模型使得生成图像的细节质量更高其中 base 模型也可以单独使用直接生成
本文将介绍如何使用 diffusers 进行 text-to-image、image-to-image 和 inpainting。
加载模型参数
模型参数分别保存在不同的子目录中可以使用 from_pretrained 方法来加载
from diffusers import StableDiffusionXLPipeline, StableDiffusionXLImg2ImgPipeline
import torchpipeline StableDiffusionXLPipeline.from_pretrained(stabilityai/stable-diffusion-xl-base-1.0, torch_dtypetorch.float16, variantfp16, use_safetensorsTrue
).to(cuda)refiner StableDiffusionXLImg2ImgPipeline.from_pretrained(stabilityai/stable-diffusion-xl-refiner-1.0, torch_dtypetorch.float16, use_safetensorsTrue, variantfp16
).to(cuda)也可以使用 from_single_file 方法来从单个文件 ( .ckpt 或 .safetensors) 中加载
from diffusers import StableDiffusionXLPipeline, StableDiffusionXLImg2ImgPipeline
import torchpipeline StableDiffusionXLPipeline.from_single_file(https://huggingface.co/stabilityai/stable-diffusion-xl-base-1.0/blob/main/sd_xl_base_1.0.safetensors, torch_dtypetorch.float16, variantfp16, use_safetensorsTrue
).to(cuda)refiner StableDiffusionXLImg2ImgPipeline.from_single_file(https://huggingface.co/stabilityai/stable-diffusion-xl-refiner-1.0/blob/main/sd_xl_refiner_1.0.safetensors, torch_dtypetorch.float16, use_safetensorsTrue, variantfp16
).to(cuda)text-to-image
在进行 text-to-image 生成时需要传入文本 prompt。SDXL 默认生成分辨率为 1024 * 1024也可以设置为 768 或 512但不要再低于 512 了
from diffusers import AutoPipelineForText2Image
import torchpipeline_text2image AutoPipelineForText2Image.from_pretrained(stabilityai/stable-diffusion-xl-base-1.0, torch_dtypetorch.float16, variantfp16, use_safetensorsTrue
).to(cuda)prompt Astronaut in a jungle, cold color palette, muted colors, detailed, 8k
image pipeline_text2image(promptprompt).images[0]
imageimage-to-image
在进行 image-to-image 生成时SDXL 在 768 - 1024 这个分辨率区间工作的最好。此时需要输入一张原始图像并给一段文本 prompt
from diffusers import AutoPipelineForImage2Image
from diffusers.utils import load_image, make_image_grid# 使用 from_pipe避免在加载 checkpoint 时消耗额外的内存
pipeline AutoPipelineForImage2Image.from_pipe(pipeline_text2image).to(cuda)url https://huggingface.co/datasets/huggingface/documentation-images/resolve/main/diffusers/sdxl-text2img.png
init_image load_image(url)
prompt a dog catching a frisbee in the jungle
image pipeline(prompt, imageinit_image, strength0.8, guidance_scale10.5).images[0]
make_image_grid([init_image, image], rows1, cols2)inpainting
在记性 inpainting 时需要传入一张原始图片和原始图片中你想要修改部分的 mask 图并给一个文本 prompt 来描述 mask 区域需要生成什么内容
from diffusers import AutoPipelineForInpainting
from diffusers.utils import load_image, make_image_gridpipeline AutoPipelineForInpainting.from_pipe(pipeline_text2image).to(cuda)img_url https://huggingface.co/datasets/huggingface/documentation-images/resolve/main/diffusers/sdxl-text2img.png
mask_url https://huggingface.co/datasets/huggingface/documentation-images/resolve/main/diffusers/sdxl-inpaint-mask.pnginit_image load_image(img_url)
mask_image load_image(mask_url)prompt A deep sea diver floating
image pipeline(promptprompt, imageinit_image, mask_imagemask_image, strength0.85, guidance_scale12.5).images[0]
make_image_grid([init_image, mask_image, image], rows1, cols3)refine image quality
SDXL 相比于之前的 SD 模型一个很大的差别在于它包含了一个 refiner 模型。refiner 模型 可以接收 base 模型经过几步去噪之后的低噪声图像并为图像生成更多高质量的细节。有两种使用 refiner 模型的方式
同时使用 base 模型和 refiner 模型来生成高质量图片使用 base 模型生成一张图片然后使用 refiner 模型为图片添加更多的细节这是 SDXL 训练时的方式
接下来分别介绍这两种方式的使用。
base refiner model
当使用第一种方式即同时使用 base 模型和 refiner 模型来生成图片时称为 ensemble of expert denoisers。这种方式相比于第二种将 base 模型的输出给 refiner 模型中的方式来说整体需要的去噪步数更少因此会快很多。但这种方式我们看到的 base 模型的输出是带有一些噪声的。
在第一种方式中base 模型负责高噪声阶段的去噪refiner 模型负责低噪声阶段的去噪。首先加载 base 模型和 refiner 模型
from diffusers import DiffusionPipeline
import torchbase DiffusionPipeline.from_pretrained(stabilityai/stable-diffusion-xl-base-1.0, torch_dtypetorch.float16, variantfp16, use_safetensorsTrue
).to(cuda)refiner DiffusionPipeline.from_pretrained(stabilityai/stable-diffusion-xl-refiner-1.0,text_encoder_2base.text_encoder_2,vaebase.vae,torch_dtypetorch.float16,use_safetensorsTrue,variantfp16,
).to(cuda)在使用 ensemble of expert denoisers 这种方式时我们需要定义不同的模型在他们各自阶段的去噪步数。对于 base 模型需要 denoising_end 参数对于 refiner 模型需要 denoising_start 参数。
denoising_start 和 denoising_end 参数都时 0-1 之间的一个小数用于表示当前 schduler 下步数的比例。如果同时还传入了 strength 参数它将被忽略因为去噪步骤的数量是由模型训练的离散时间步长和声明的比例截止值决定的。
这里我们设置 denoising_end 为 0.8从而 base 模型会负责前 80% 的高噪声阶段的降噪并设置 denoising_start 为 0.8从而 refiner 模型会负责后 20% 的低噪声阶段的降噪。注意 base 模型的输出是在隐层 latent 空间的而非可见的图片。
prompt A majestic lion jumping from a big stone at nightimage base(promptprompt,num_inference_steps40,denoising_end0.8,output_typelatent,
).images
image refiner(promptprompt,num_inference_steps40,denoising_start0.8,imageimage,
).images[0]
image在 StableDiffusionXLInpaintPipeline 中refiner 模型也可以用于进行 inpainting
from diffusers import StableDiffusionXLInpaintPipeline
from diffusers.utils import load_image, make_image_grid
import torchbase StableDiffusionXLInpaintPipeline.from_pretrained(stabilityai/stable-diffusion-xl-base-1.0, torch_dtypetorch.float16, variantfp16, use_safetensorsTrue
).to(cuda)refiner StableDiffusionXLInpaintPipeline.from_pretrained(stabilityai/stable-diffusion-xl-refiner-1.0,text_encoder_2base.text_encoder_2,vaebase.vae,torch_dtypetorch.float16,use_safetensorsTrue,variantfp16,
).to(cuda)img_url https://raw.githubusercontent.com/CompVis/latent-diffusion/main/data/inpainting_examples/overture-creations-5sI6fQgYIuo.png
mask_url https://raw.githubusercontent.com/CompVis/latent-diffusion/main/data/inpainting_examples/overture-creations-5sI6fQgYIuo_mask.pnginit_image load_image(img_url)
mask_image load_image(mask_url)prompt A majestic tiger sitting on a bench
num_inference_steps 75
high_noise_frac 0.7image base(promptprompt,imageinit_image,mask_imagemask_image,num_inference_stepsnum_inference_steps,denoising_endhigh_noise_frac,output_typelatent,
).images
image refiner(promptprompt,imageimage,mask_imagemask_image,num_inference_stepsnum_inference_steps,denoising_starthigh_noise_frac,
).images[0]
make_image_grid([init_image, mask_image, image.resize((512, 512))], rows1, cols3)这种 ensemble of expert denoisers 的方式对于所有 scheduler 都可用。
base to refiner model
第二种方式通过 base 模型先生成一张完全去噪的图片然后使用 refiner 模型以 image-to-image 的形式为图片添加更多的高质量细节这使得 SDXL 的生成质量有了极大的提高。首先加载 base 和 refiner 模型
from diffusers import DiffusionPipeline
import torchbase DiffusionPipeline.from_pretrained(stabilityai/stable-diffusion-xl-base-1.0, torch_dtypetorch.float16, variantfp16, use_safetensorsTrue
).to(cuda)refiner DiffusionPipeline.from_pretrained(stabilityai/stable-diffusion-xl-refiner-1.0,text_encoder_2base.text_encoder_2,vaebase.vae,torch_dtypetorch.float16,use_safetensorsTrue,variantfp16,
).to(cuda)先使用 base 模型生成一张图片注意将输出形式设置为 latent
prompt Astronaut in a jungle, cold color palette, muted colors, detailed, 8kimage base(promptprompt, output_typelatent).images[0]将生成的图片输入到 refiner 模型中
image refiner(promptprompt, imageimage[None, :]).images[0]要进行 inpainting在 StableDiffusionXLInpaintPipeline 中加载 base 和 refiner 模型去掉 denoising_end 和 denoising_start 参数并为 refiner 模型设置一个较小的步数。
micro-conditioning
SDXL 训练时使用了许多额外的条件方式即 micro-conditioning包括 original_image_size、target_image_size 和 cropping parameters。在推理阶段合理地使用 micro-conditioning 可以生成高质量的、居中的图片。
由于 classfier-free guidance 的存在可以在 SDXL 相关的 pipeline 中使用 micro-conditioning 和 negative micro-conditioning 参数。
size conditioning
size conditioning 有两种 original size conditioning。训练集中有许多图片的分辨率是较低的但又不能直接不用这些低分辨率图像占比达 40%丢了太浪费了因此通常会对这些图像进行 resize从而得到高分辨率的图像。在这个过程中不可避免得会引入插值这种人工合成的模糊痕迹被 SDXL 学到而在真正的高分辨率图像中是不该有这些痕迹的。因此训练时会告诉模型这张图片实际是多少分辨率的作为条件。 在推理阶段我们可以指定 original_size 来表示图像的原始尺寸。使用默认的 1024能生成出与原始数据集中高分辨率图像类似的高质量图像。而如果将这个值设得很低如 256模型还是会生成分辨率为 1024 的图像但就会带有低分辨率图像的特征如模糊、模式简单等。 target size conditioning。SDXL 训练时支持多种不同的长宽比。 推理时如果使用默认的值 1024生成的图像会看起来像方形图像长宽比1:1。这里建议将 target_size 和 original_size 设置为相同的值但你也可以调一调这些参数实验一下看看。
在 diffusers 中我们还可以指定有关图像大小的 negative 条件从而引导生成远离某些图像分辨率
from diffusers import StableDiffusionXLPipeline
import torchpipe StableDiffusionXLPipeline.from_pretrained(stabilityai/stable-diffusion-xl-base-1.0, torch_dtypetorch.float16, variantfp16, use_safetensorsTrue
).to(cuda)prompt Astronaut in a jungle, cold color palette, muted colors, detailed, 8k
image pipe(promptprompt,negative_original_size(512, 512),negative_target_size(1024, 1024),
).images[0]crop conditioning
SDXL 之前的 SD 模型的生成结果有时会看起来像是被裁剪过得。这是因为为了保证训练时每个 batch 内的尺寸一致输入的训练数据确实有很多是裁剪过的。因此训练时裁剪坐标也会作为条件给到模型。从而在推理时我们将裁剪坐标指定为 (0, 0) 也是 diffusers 默认值就可以生成非裁剪的图片了。你也可以试着调一下裁剪坐标这个参数看模型的生成结果会是什么样子应该可以得到非居中的构图。
from diffusers import StableDiffusionXLPipeline
import torchpipeline StableDiffusionXLPipeline.from_pretrained(stabilityai/stable-diffusion-xl-base-1.0, torch_dtypetorch.float16, variantfp16, use_safetensorsTrue
).to(cuda)prompt Astronaut in a jungle, cold color palette, muted colors, detailed, 8k
image pipeline(promptprompt, crops_coords_top_left(256, 0)).images[0]
image同样可以指定 negative 裁剪坐标以引导生成远离某些裁剪参数
from diffusers import StableDiffusionXLPipeline
import torchpipe StableDiffusionXLPipeline.from_pretrained(stabilityai/stable-diffusion-xl-base-1.0, torch_dtypetorch.float16, variantfp16, use_safetensorsTrue
).to(cuda)prompt Astronaut in a jungle, cold color palette, muted colors, detailed, 8k
image pipe(promptprompt,negative_original_size(512, 512),negative_crops_coords_top_left(0, 0),negative_target_size(1024, 1024),
).images[0]
imageUse a different prompt for each text-encoder
SDXL 有两个 text encoder所以给两个 text encoder 传入不同的文本 prompt 是可能的这可以提高生成质量参考。将原本的 prompt 传到 prompt 中另一个 prompt 传到 prompt_2 中。如果使用 negative prompt 也是类似的分别传到 negative_prompt 和 negative_prompt_2 。
from diffusers import StableDiffusionXLPipeline
import torchpipeline StableDiffusionXLPipeline.from_pretrained(stabilityai/stable-diffusion-xl-base-1.0, torch_dtypetorch.float16, variantfp16, use_safetensorsTrue
).to(cuda)# prompt is passed to OAI CLIP-ViT/L-14
prompt Astronaut in a jungle, cold color palette, muted colors, detailed, 8k
# prompt_2 is passed to OpenCLIP-ViT/bigG-14
prompt_2 Van Gogh painting
image pipeline(promptprompt, prompt_2prompt_2).images[0]
imageSDXL 的双 text encoder 同样支持 textual inversion embeddings需要分别加载详情见SDXL textual inversion 。
Optimizations
SDXL 的模型还是很大的可能在一些设备上运行会比较吃力以下是一些节约内存和提高推理速度的技巧。 如果显存不够可以临时将模型 offload 到内存中 # base.to(cuda)
# refiner.to(cuda)
base.enable_model_cpu_offload()
refiner.enable_model_cpu_offload()如果你使用的 torch 版本 2.0那么使用 torch.cmpile 可以提速约 20% base.unet torch.compile(base.unet, modereduce-overhead, fullgraphTrue)
refiner.unet torch.compile(refiner.unet, modereduce-overhead, fullgraphTrue)如果你使用的 torch 版本 2.0记得要用 xFormers 来提供 flash attention base.enable_xformers_memory_efficient_attention()
refiner.enable_xformers_memory_efficient_attention()Other resources
如果你想要研究下 SDXL 中 UNet2DConditionModel 的最小版本可参考minSDXL 。