Section courante

A propos

Section administrative du site

where

Rust

Syntaxe

fn nom_fonction<T, U>(param: T) -> U
where
   T: Trait1 + Trait2,
   U: Trait3,
{
   // corps de la fonction
}

Paramètres

Nom Description
T: Trait1 + Trait2 Ce paramètre permet de contraindre le type T à implémenter les traits Trait1 et Trait2, définissant ses capacités.
U: Trait3 Ce paramètre permet de contraindre le type U à implémenter le trait Trait3, assurant une interface ou comportement spécifique.

Description

Ce mot réservé permet de dénoter des clauses contraignant un type.

Remarques

Ajoutez des contraintes à respecter pour utiliser un élément.

where permet de spécifier des contraintes sur la durée de vie et les paramètres génériques. La RFC introduisant where contient des informations détaillées sur le mot-clef.

Exemples

where peut être utilisé pour les contraintes avec des traits :

  1. fn new<T: Default>() -> T {
  2.     T::default()
  3. }
  4.  
  5. fn new_where<T>() -> T
  6. where
  7.     T: Default,
  8. {
  9.     T::default()
  10. }
  11.  
  12. assert_eq!(0.0, new());
  13. assert_eq!(0.0, new_where());
  14.  
  15. assert_eq!(0, new());
  16. assert_eq!(0, new_where());

Où peut également être utilisé pour les durées de vie.

Ceci est compilé car une durée de vie plus longue est supérieure à une durée de vie plus courte, la contrainte est donc respectée :

  1. fn select<'short, 'long>(s1: &'short str, s2: &'long str, second: bool) -> &'short str
  2. where
  3.     'long: 'short,
  4. {
  5.     if second { s2 } else { s1 }
  6. }
  7.  
  8. let outer = String::from("Longue vie ref");
  9. let longer = &outer;
  10. {
  11.     let inner = String::from("Ref de courte durée");
  12.     let shorter = &inner;
  13.  
  14.     assert_eq!(select(shorter, longer, false), shorter);
  15.     assert_eq!(select(shorter, longer, true), longer);
  16. }

D'un autre côté, cela ne compilera pas car la clause where 'b: 'a est manquante : la durée de vie de 'b n'est pas connue pour durer au moins aussi longtemps que 'a, ce qui signifie que cette fonction ne peut pas garantir qu'elle renvoie toujours une référence valide :

  1. fn select<'a, 'b>(s1: &'a str, s2: &'b str, second: bool) -> &'a str
  2. {
  3.     if second { s2 } else { s1 }
  4. }

où peut également être utilisé pour exprimer des contraintes plus complexes qui ne peuvent pas être écrites avec la syntaxe <T: Trait> :

  1. fn first_or_default<I>(mut i: I) -> I::Item
  2. where
  3.     I: Iterator,
  4.     I::Item: Default,
  5. {
  6.     i.next().unwrap_or_else(I::Item::default)
  7. }
  8.  
  9. assert_eq!(first_or_default([1, 2, 3].into_iter()), 1);
  10. assert_eq!(first_or_default(Vec::<i32>::new().into_iter()), 0);

où est disponible partout où les paramètres génériques et à vie sont disponibles, comme on peut le voir avec le type Cow de la bibliothèque standard :

  1. pub enum Cow<'a, B>
  2. where
  3.     B: ToOwned + ?Sized,
  4. {
  5.     Borrowed(&'a B),
  6.     Owned(<B as ToOwned>::Owned),
  7. }


Dernière mise à jour : Vendredi, le 1er Août 2025