È vero che per tutti i tipi "T", "U" se "T" è costretto a "U" allora "& T" è costretto a "& U"?

Aug 17 2020

È ben documentato che [T; n]può costringere a farlo [T]. Anche il codice seguente è ben formato :

fn test(){
    let _a: &[i32] = &[1, 2, 3];
}

Qui abbiamo che &[T; n]è costretto a farlo &[T].

È vero che per tutti i tipi T, Use Tè costretto a, Uallora &Tè costretto a farlo &U?

Non è documentato nel riferimento (almeno esplicitamente).

Risposte

5 trentcl Aug 17 2020 at 19:54

No, perché l'aggiunta di un altro livello di &causa fallisce:

fn oops() {
    let a: &[i32; 3] = &[1, 2, 3];
    let _b: &&[i32] = &a;
}
error[E0308]: mismatched types
 --> src/lib.rs:8:23
  |
8 |     let _b: &&[i32] = &a;
  |             -------   ^^ expected slice `[i32]`, found array `[i32; 3]`
  |             |
  |             expected due to this
  |
  = note: expected reference `&&[i32]`
             found reference `&&[i32; 3]`

Inoltre, non è il caso che [T; n] costringa a [T] nello stesso senso in cui &[T; n] costringe a &[T] . La documentazione che hai collegato descrive i due tratti relativi alle coercizioni non dimensionate: Unsizee CoerceUnsized. [T; n]implementa Unsize<[T]>, e quindi &[T; n] implementa CoerceUnsized<&[T]>; questa è essenzialmente la stessa cosa e il tuo codice dimostra efficacemente entrambi. Non sarebbe possibile scrivere una funzione che esercita una coercizione [T; n]a [T] senza usando i riferimenti (o puntatori di qualche tipo) a causa coercizioni unsizing solo prendere posto alle spalle di un qualche tipo di puntatore.