Diffusion Models: как работают Stable Diffusion и DALL-E
opensourceaimldeep-learningit
Введение: от GAN к Diffusion
До 2022 года генерацией изображений правили GAN (Generative Adversarial Networks):
GAN архитектура:
Generator: noise → изображение
Discriminator: изображение → real/fake
Generator и Discriminator соревнуются:
Generator пытается обмануть Discriminator
Discriminator пытается поймать Generator
Проблема: нестабильное обучение, mode collapse
Diffusion Models (2015-2020) — новый подход, который оказался стабильнее и качественнее:
Diffusion Model:
Forward: изображение → шум за T шагов
Reverse: шум → изображение за T шагов
Обучение: предсказывать шум на каждом шаге
Стабильнее GAN, нет проблем с mode collapse
Ключевые статьи:
- "Denoising Diffusion Probabilistic Models" (DDPM, 2020)
- "High-Image-Resolution Synthesis with Latent Diffusion Models" (LDM, 2021)
- "High-Resolution Image Synthesis with Latent Diffusion Models" (Stable Diffusion, 2022)
Forward process: добавление шума
Как работает diffusion
Forward process (детерминированный):
x₀ = исходное изображение
xₜ = √ᾱₜ × x₀ + √(1-ᾱₜ) × ε, ε ~ N(0, I)
где ᾱₜ = ∏ᵢ₌₁ᵗ (1 - βᵢ)
βᵢ — schedule noise (от 0.0001 до 0.02)
T = 1000 шагов:
x₀ → x₁ → x₂ → ... → x₉₉₉ → x₁₀₀₀
x₁₀₀₀ ≈ N(0, I) — чистый Gaussian noise
Визуализация
Forward diffusion (1000 шагов):
Шаг 0: 🖼️ [чёткое изображение]
Шаг 10: 🖼️ [лёгкий шум]
Шаг 100: 🖼️ [умеренный шум]
Шаг 500: 🖼️ [сильный шум]
Шаг 1000: 📺 [белый шум, N(0, I)]
Noise schedule
# Noise schedule (linear)
T = 1000
beta = torch.linspace(0.0001, 0.02, T)
alpha = 1 - beta
alpha_hat = torch.cumprod(alpha) # кумулятивный продукт
# Для шага t=500:
# alpha_hat[500] ≈ 0.5
# x_500 = sqrt(0.5) * x_0 + sqrt(0.5) * noise
Reverse process: удаление шума
Что обучает модель
Reverse process (генерация):
p_θ(x_{t-1} | x_t) = N(x_{t-1}; μ_θ(x_t, t), σ_t²)
Модель U-Net предсказывает:
1. Mean: μ_θ(x_t, t)
2. Variance: σ_t² (часто фиксировано)
Или модель предсказывает noise ε_θ:
ε_θ(x_t, t) → предсказание шума
x_{t-1} = (x_t - (1-α_t) × ε_θ) / sqrt(α_t) + σ_t × z
U-Net архитектура
U-Net для diffusion:
┌──────────┐
│ x_t │ ← зашумлённое изображение
│ (t, 64) │
└────┬─────┘
│
┌────▼─────┐
│ Time │ ← timestep embedding
│ embed │ t → sin/cos embedding
└────┬─────┘
│
┌──────────▼──────────┐
│ Encoder │
│ (downsampling) │
│ 64 → 128 → 256 │
└──────────┬──────────┘
│
┌──────────▼──────────┐
│ Bottleneck │
│ (256 channels) │
└──────────┬──────────┘
│
┌──────────▼──────────┐
│ Decoder │
│ (upsampling) │
│ 256 → 128 → 64 │
└──────────┬──────────┘
│
┌────▼─────┐
│ ε_θ │ ← предсказанный шум
└──────────┘
Training loss
# Simple MSE loss на предсказание шума
def diffusion_loss(model, x_0, t):
"""
x_0: исходное изображение
t: timestep (0..T-1)
"""
noise = torch.randn_like(x_0)
# Add noise (reparameterization)
x_t = sqrt_alpha_hat[:, t] * x_0 + sqrt_one_minus_alpha_hat[:, t] * noise
# Predict noise
predicted_noise = model(x_t, t)
# MSE loss
loss = MSE(noise, predicted_noise)
return loss
Latent Diffusion (Stable Diffusion)
Проблема: pixel-space diffusion медленный
Pixel-space DDPM:
Изображение: 512 × 512 × 3 = 786,432 пикселей
U-Net обрабатывает 786K значений × 1000 шагов
Для 1024×1024: 4× больше памяти и времени!
Решение: Latent Diffusion
VAE (Variational Autoencoder):
Encoder: изображение → latent space (8× меньше)
Decoder: latent → изображение
512 × 512 × 3 → 64 × 64 × 4 = 16,384 latent dims
1024 × 1024 × 3 → 128 × 128 × 4 = 65,536 latent dims
Latent Diffusion:
Diffusion происходит в latent space
U-Net обрабатывает 64×64 вместо 512×512
= 64x быстрее по памяти, ~8x быстрее по времени
Stable Diffusion архитектура
Stable Diffusion v1.4 (512×512):
VAE Encoder:
512 × 512 × 3 → 4 × 64 × 64 (latent)
Latent Diffusion:
U-Net в latent space
Cross-attention с text embeddings
VAE Decoder:
4 × 64 × 64 → 512 × 512 × 3
Text-to-Image: CLIP и Cross-Attention
Как текст управляет генерацией
Text-to-Image pipeline:
Text → CLIP Text Encoder → text embeddings (77 × 768)
U-Net:
Input: latent + timestep
Cross-Attention:
Q = from U-Net features
K, V = from text embeddings
Attention(Q, K, V) = softmax(Q @ K^T / sqrt(d)) @ V
→ U-Net "смотрит" на текст на каждом шаге
Визуализация cross-attention
Для каждого шага reverse diffusion:
Текст: "a cat sitting on a windowsill"
Cross-attention позволяет U-Net:
- Знать, ЧТО рисовать (cat)
- Знать, ГДЕ рисовать (windowsill)
- Знать, КАК рисовать (sitting)
Генерация: пошаговый процесс
Полный pipeline
# Генерация изображения (упрощённо)
def generate_image(prompt, steps=50, cfg=7.5):
# 1. Encode text
text_emb = clip_encoder(prompt)
# 2. Start from random noise
x_T = torch.randn(1, 4, 64, 64) # latent space
# 3. Reverse diffusion
for t in reversed(range(T)):
# Predict noise
noise_pred = unet(x_t, t, text_emb)
# Classifier-free guidance
noise_uncond = unet(x_t, t, None)
noise = noise_uncond + cfg * (noise_pred - noise_uncond)
# Step back
x_t = step_back(x_t, noise, t)
# 4. Decode latent to image
image = vae_decoder(x_0)
return image
Classifier-Free Guidance
CFG — управление стилем/точностью:
cfg = 1.0 → только текст (менее точный)
cfg = 7.5 → баланс (стандарт Stable Diffusion)
cfg = 15.0 → строго по тексту (может быть артефакты)
noise = noise_unconditional + cfg × (
noise_conditional - noise_unconditional
)
Steps и качество
Steps → качество:
20 steps: быстрая генерация, среднее качество
50 steps: стандарт, хорошее качество
100 steps: максимальное качество
Для 512×512 на A100:
20 steps: ~2 секунды
50 steps: ~5 секунд
100 steps: ~10 секунд
Ускорение генерации
DPM-Solver и другие samplers
Обычный Euler sampler:
x_{t-1} = x_t - β_t × ε_θ
Требует 50-100 шагов для хорошего качества
DPM-Solver (2022):
Более умная дискретизация ODE
10-20 шагов = 50 шагов Euler
На 3-5x быстрее при том же качестве
Latent Consistency Models (LCM)
LCM — distilled LCM:
Обучается на 1-4 шага
LCM-SDXL:
4 steps = качество 50 steps SDXL
На диск 20x быстрее Stable Diffusion
LCM-Lora:
Допил для существующих моделей
4 steps за ~1 секунду на RTX 4090
TensorRT-LLM и оптимизации
Оптимизации для inference:
1. FP16 / FP8 квантизация
2. TensorRT / ONNX Runtime
3. Kernel fusion (UNet + VAE)
4. Batch processing
RTX 4090:
Обычный: 8 секунд на изображение
Оптимиз: 1.5 секунды на изображение
ControlNet и IP-Adapter
ControlNet: контроль позы/линий
ControlNet — добавляет контроль:
- Pose (поза человека)
- Canny (края изображения)
- Depth (глубина)
- Scribble (набросок)
Работает так:
Копия U-Net заморажена
Обучается только "zero convolution" слой
Не портит оригинальную модель
IP-Adapter: контроль по изображению
IP-Adapter — по аналогии с CLIP:
Input: reference image → image embedding
Cross-attention с image embedding
Результат:
Сохраняет стиль/reference image
Не требует дообучения
Open Source экосистема
Stable Diffusion модели
Stable Diffusion v1.5:
512×512, 860M параметров
Лучшая для community моделей
Checkpoints:
DreamShaper — универсальная
RealisticVision — фотореализм
DreamLike — арт
LoRA:
Hundreds of community LoRA
ControlNet:
10+ control types
SDXL
SDXL (Stable Diffusion XL):
1024×1024
2.6B параметров
Better composition, text
Refiner model:
Base: 1024×1024 (rough)
Refiner: 1024×1024 (details)
Turbo: 1 step generation
ComfyUI и Automatic1111
Automatic1111:
Web UI для SD
Простой интерфейс
Extensions: ADetailer, ControlNet
ComfyUI:
Node-based UI
Более гибкий
Better performance
Custom workflows
Diffusion для не-изображений
Audio diffusion
Audio Diffusion:
Audio → spectrogram → 2D "image"
Diffusion на spectrogram
Griffin-Lim для обратного преобразования
Примеры:
AudioLDM — text-to-audio
MusicLDM — text-to-music
Video diffusion
Video Diffusion:
3D U-Net (time + spatial)
Space-time attention
Примеры:
Stable Video Diffusion
ModelScope Text-to-Video
AnimateDiff (animation from text)
3D diffusion
3D Diffusion:
Point clouds / voxels / meshes
Генерация 3D объектов
Примеры:
DreamFusion — text-to-3D
Zero123 — image-to-3D
Сравнение: GAN vs Diffusion
GAN (StyleGAN3):
+ Быстрая генерация (1 проход)
+ Хорошие результаты
- Нестабильное обучение
- Mode collapse
- Трудно контролировать
Diffusion (Stable Diffusion):
+ Стабильное обучение
+ Хороший контроль (text, pose, etc.)
+ Better diversity
- Медленная генерация (1000 шагов)
- Больше памяти
Итоги
Diffusion models — state-of-the-art для:
- Text-to-image (Stable Diffusion, DALL-E)
- Image editing (inpainting, outpainting)
- Super-resolution (ESRGAN + diffusion)
- 3D generation (DreamFusion)
- Video generation (Sora, SVD)
Рекомендации:
1. Для генерации изображений — Stable Diffusion
2. Для контроля — ControlNet + IP-Adapter
3. Для скорости — LCM или DPM-Solver
4. Для качества — SDXL + Refiner