# Planificateurs

Un planificateur indique à la boucle de débruitage la quantité de bruit à éliminer à chaque étape. Les différents planificateurs offrent un compromis entre la vitesse et la qualité.

Ce guide montre comment charger un planificateur et personnaliser son calendrier de pas de temps, son espacement et ses sigmas.

## Choisir un planificateur

Commencez à partir du point de contrôle par défaut. N’effectuez un remplacement que si vous avez besoin d’un compromis différent entre vitesse et qualité.

- DPM++ 2M SDE Karras est une option polyvalente et performante pour de nombreux points de contrôle de diffusion latente.
- [TCDScheduler](/docs/diffusers/main/fr/api/schedulers/tcd#diffusers.TCDScheduler) fonctionne bien pour les modèles distillés.
- Utilisez [FlowMatchEulerDiscreteScheduler](/docs/diffusers/main/fr/api/schedulers/flow_match_euler_discrete#diffusers.FlowMatchEulerDiscreteScheduler) ou [FlowMatchHeunDiscreteScheduler](/docs/diffusers/main/fr/api/schedulers/flow_match_heun_discrete#diffusers.FlowMatchHeunDiscreteScheduler) pour les modèles FlowMatch (Qwen-Image, Flux et similaires).
- [EulerDiscreteScheduler](/docs/diffusers/main/fr/api/schedulers/euler#diffusers.EulerDiscreteScheduler) ou [EulerAncestralDiscreteScheduler](/docs/diffusers/main/fr/api/schedulers/euler_ancestral#diffusers.EulerAncestralDiscreteScheduler) fonctionnent souvent bien pour les images de style anime.
- [LCMScheduler](/docs/diffusers/main/fr/api/schedulers/lcm#diffusers.LCMScheduler) avec un UNet LCM ou un LoRA pour une génération en peu d'étapes lorsque le checkpoint le prend en charge.

## Chargement des planificateurs

> [!TIP]
> Les modèles de flow-matching tels que Qwen-Image et Flux livrent [FlowMatchEulerDiscreteScheduler](/docs/diffusers/main/fr/api/schedulers/flow_match_euler_discrete#diffusers.FlowMatchEulerDiscreteScheduler) par défaut. Conservez ce planificateur à moins d’expérimenter délibérément. Remplacez-le via [from_config()](/docs/diffusers/main/fr/api/configuration#diffusers.ConfigMixin.from_config) uniquement si le substitut est compatible avec le point de contrôle.

Les planificateurs ne contiennent que des configurations et ne fournissent pas de tenseurs de poids. Accédez à l'attribut `.scheduler` d'un pipeline pour inspecter la configuration chargée.

```py
import torch
from diffusers import DiffusionPipeline

pipeline = DiffusionPipeline.from_pretrained(
    "stabilityai/stable-diffusion-xl-base-1.0", dtype=torch.float16, device_map="cuda"  # or "mps", "xpu", "cpu"
)
pipeline.scheduler
```

Pour remplacer les planificateurs d'un pipeline chargé, utilisez [from_config()](/docs/diffusers/main/fr/api/configuration#diffusers.ConfigMixin.from_config) avec la configuration du planificateur existant afin que `num_train_timesteps` et les champs associés restent alignés. Pour les points de contrôle FlowMatch (Qwen-Image, Flux et similaires), conservez [FlowMatchEulerDiscreteScheduler](/docs/diffusers/main/fr/api/schedulers/flow_match_euler_discrete#diffusers.FlowMatchEulerDiscreteScheduler) à moins d'expérimenter délibérément avec un remplacement compatible.

```py
from diffusers import DPMSolverMultistepScheduler

pipeline.scheduler = DPMSolverMultistepScheduler.from_config(pipeline.scheduler.config)
```

Vous pouvez également charger une configuration de planificateur depuis le Hub avec [from_pretrained()](/docs/diffusers/main/fr/api/schedulers/overview#diffusers.SchedulerMixin.from_pretrained) et la transmettre à [from_pretrained()](/docs/diffusers/main/fr/api/pipelines/overview#diffusers.DiffusionPipeline.from_pretrained) via `scheduler`.

```py
from diffusers import DiffusionPipeline, DPMSolverMultistepScheduler

dpm = DPMSolverMultistepScheduler.from_pretrained(
    "stabilityai/stable-diffusion-xl-base-1.0", subfolder="scheduler"
)
pipeline = DiffusionPipeline.from_pretrained(
    "stabilityai/stable-diffusion-xl-base-1.0",
    scheduler=dpm,
    dtype=torch.float16,
    device_map="cuda",  # or "mps", "xpu", "cpu"
)
pipeline.scheduler
```

## Plans de pas de temps

Le timestep ou le plan de bruit détermine la manière dont le bruit est réparti au cours du processus de débruitage. Le plan peut être linéaire ou plus concentré vers le début ou la fin. Il s'agit d'une séquence précalculée de niveaux de bruit générée à partir de la configuration par défaut du planificateur, mais elle peut être personnalisée pour utiliser d'autres plans.

```text
linear (even steps)                 AYS (denser where it matters)
noise                               noise
  ^                                   ^
  | *                                 | *
  |  *                                |   *
  |   *                               |    **
  |    *                              |     ***
  |     *                             |      **
  |      *                            |        *
  |       *                           |          *
  +-----------------> step            +-----------------> step
```

> [!TIP]
> Les `timesteps` personnalisés ne fonctionnent que si la méthode `set_timesteps` de ce planificateur accepte cet argument (les pipelines vérifient la signature via `retrieve_timesteps` et lèvent une `ValueError` dans le cas contraire). Consultez la page API du planificateur ou la signature de `set_timesteps` avant de les transmettre.

L'exemple ci-dessous utilise le planning [Align Your Steps (AYS)](https://research.nvidia.com/labs/toronto-ai/AlignYourSteps/), qui peut générer une image de haute qualité en 10 étapes, accélérant considérablement la génération et réduisant le temps de calcul.

Importez le planning et passez-le à l'argument `timesteps` dans le pipeline.

```py
import torch
from diffusers import DiffusionPipeline, DPMSolverMultistepScheduler
from diffusers.schedulers import AysSchedules

sampling_schedule = AysSchedules["StableDiffusionXLTimesteps"]
print(sampling_schedule)
# [999, 845, 730, 587, 443, 310, 193, 116, 53, 13]

pipeline = DiffusionPipeline.from_pretrained(
    "SG161222/RealVisXL_V4.0",
    dtype=torch.float16,
    device_map="cuda"  # or "mps", "xpu", "cpu"
)
pipeline.scheduler = DPMSolverMultistepScheduler.from_config(
  pipeline.scheduler.config, algorithm_type="sde-dpmsolver++"
)

prompt = "A cinematic shot of a cute little rabbit wearing a jacket and doing a thumbs up"
image = pipeline(
    prompt=prompt,
    negative_prompt="",
    timesteps=sampling_schedule,
).images[0]
```

  
    
    Plan de pas de temps AYS 10 étapes
  
  
    
    Planification des pas de temps linéairement espacés 10 étapes
  
  
    
    Planification des pas de temps linéairement espacés 25 pas
  

Pour le rééchelonnement v-prediction/zero-SNR sur les anciens points de contrôle, voir [Points de contrôle legacy](./legacy_checkpoints#rescaling-schedules).

## Espacement des pas de temps

L'espacement des timesteps désigne les étapes spécifiques *t* à échantillonner à partir du planning. Diffusers propose trois types d'espacement, présentés ci-dessous.

| stratégie d'espacement | calcul de l'espacement | étapes de temps d'exemple |
|---|---|---|
| `leading` | étapes régulièrement espacées | `[900, 800, 700, ..., 100, 0]` |
| `linspace` | inclure les étapes première et dernière et répartir uniformément les étapes intermédiaires restantes | `[1000, 888.89, 777.78, ..., 111.11, 0]` |
| `trailing` | inclure la dernière étape et répartir uniformément les étapes intermédiaires restantes en partant de la fin | `[999, 899, 799, 699, 599, 499, 399, 299, 199, 99]` |

Transmettez la stratégie d'espacement à l'argument `timestep_spacing` dans le planificateur.

> [!TIP]
> La stratégie `trailing` produit généralement des images de meilleure qualité, avec plus de détails, en moins d'étapes, mais la différence de qualité n'est pas aussi évidente pour des valeurs d'étapes plus standard.

```py
import torch
from diffusers import DiffusionPipeline, DPMSolverMultistepScheduler

pipeline = DiffusionPipeline.from_pretrained(
    "SG161222/RealVisXL_V4.0",
    dtype=torch.float16,
    device_map="cuda"  # or "mps", "xpu", "cpu"
)
pipeline.scheduler = DPMSolverMultistepScheduler.from_config(
  pipeline.scheduler.config, timestep_spacing="trailing"
)

prompt = "A cinematic shot of a cute little black cat sitting on a pumpkin at night"
image = pipeline(
    prompt=prompt,
    negative_prompt="",
    num_inference_steps=5,
).images[0]
image
```

  
    
    espacement final après 5 étapes
  
  
    
    espacement de tête après 5 étapes
  

## Sigmas

Sigmas est une mesure du niveau de bruit d'un échantillon à une étape donnée, telle que définie par le planning. Lors de l'utilisation de `sigmas` personnalisés, les `timesteps` sont calculés à partir de ces valeurs au lieu de la configuration par défaut du planificateur.

```text
step:   0    1    2    3    4
sigma:  σ0 > σ1 > σ2 > σ3 > σ4 ≈ 0
        high noise  --->  clean sample
```

> [!TIP]
> Les `sigmas` personnalisés ne fonctionnent que si la méthode `set_timesteps` de ce planificateur accepte cet argument (les pipelines vérifient la signature via `retrieve_timesteps` et lèvent une `ValueError` dans le cas contraire). Consultez la page API du planificateur ou la signature de `set_timesteps` avant de les transmettre.

Passez les sigmas personnalisés à l'argument `sigmas` du pipeline. L'exemple ci-dessous utilise les [sigmas](https://github.com/huggingface/diffusers/blob/main/src/diffusers/schedulers/scheduling_utils.py) de l'agenda AYS en 10 étapes.

```py
import torch
from diffusers import DiffusionPipeline, EulerDiscreteScheduler
from diffusers.schedulers import AysSchedules

pipeline = DiffusionPipeline.from_pretrained(
    "SG161222/RealVisXL_V4.0",
    dtype=torch.float16,
    device_map="cuda",  # or "mps", "xpu", "cpu"
)
pipeline.scheduler = EulerDiscreteScheduler.from_config(pipeline.scheduler.config)

sigmas = AysSchedules["StableDiffusionXLSigmas"]
prompt = "A cinematic shot of a cute little rabbit wearing a jacket and doing a thumbs up"
image = pipeline(
    prompt=prompt,
    negative_prompt="",
    sigmas=sigmas,
).images[0]
```

### Sigmas de Karras

[Karras sigmas](https://huggingface.co/papers/2206.00364) rééchantillonne le plan de bruit pour un échantillonnage plus efficace en regroupant les sigmas plus densément au milieu de la séquence, là où la reconstruction de la structure est cruciale, tout en utilisant moins de sigmas au début et à la fin, où les variations de bruit ont moins d’impact. Cela peut augmenter le niveau de détails d’une image générée.

```text
default σ:  *  *  *  *  *  *  *  *     even-ish
Karras σ:   *   * * * * *   *          denser mid, sparser ends
            |---structure---|
```

Définissez `use_karras_sigmas=True` dans le planificateur pour l'activer.

```py
import torch
from diffusers import DiffusionPipeline, DPMSolverMultistepScheduler

pipeline = DiffusionPipeline.from_pretrained(
    "SG161222/RealVisXL_V4.0",
    dtype=torch.float16,
    device_map="cuda"  # or "mps", "xpu", "cpu"
)
pipeline.scheduler = DPMSolverMultistepScheduler.from_config(
  pipeline.scheduler.config,
  algorithm_type="sde-dpmsolver++",
  use_karras_sigmas=True,
)

prompt = "A cinematic shot of a cute little rabbit wearing a jacket and doing a thumbs up"
image = pipeline(
    prompt=prompt,
    negative_prompt="",
    num_inference_steps=20,
).images[0]
```

  
    
    Sigmas de Karras activés
  
  
    
    Karras sigmas désactivés
  

Reportez-vous à l’[aperçu](../api/schedulers/overview) de l’API du planificateur pour obtenir la liste des planificateurs prenant en charge les sigmas de Karras. Il ne doit être utilisé que pour les modèles entraînés avec des sigmas de Karras.

## Étapes suivantes

- Lisez l'article [Common Diffusion Noise Schedules and Sample Steps are Flawed](https://huggingface.co/papers/2305.08891) pour plus de détails sur le rééchelonnement du bruit pour imposer un SNR nul.

