sintassi della ruggine:motivo di &mut foo invece di &foo in ruggine quando foo ha dichiarato mut

StackOverflow https://stackoverflow.com//questions/25091631

  •  02-01-2020
  •  | 
  •  

Domanda

Per una routine c come

MPI_Comm_rank(MPI_Comm comm, int *rank);

l'interfaccia della funzione Rust Foreign potrebbe essere dichiarata in questo modo:

extern crate libc;
use libc::{c_int};

#[link(name = "mpi")]
extern {
    fn MPI_Comm_rank(mpi_comm: c_int,
                     rank: *mut c_int);
}

Chiamo l'associazione in questo modo, che funziona, ma mi ha lasciato perplesso sulla sintassi:

pub static MPI_COMM_WORLD : libc::c_int = 0x44000000;
fn main() {

    let mut rank: c_int = 999999;
    /* but why '&mut rank' and not simply '&rank' ? */
    unsafe {MPI_Comm_rank(MPI_COMM_WORLD, &mut rank)}
}       

Inizialmente ho provato

unsafe {MPI_Comm_rank(MPI_COMM_WORLD, &rank)}

ma questo dà un errore del compilatore:

mismatched types: expected `*mut i32` but found `&i32` (values differ in mutability)

Ho dichiarato 'rank' come mut, quindi cosa succede?

È stato utile?

Soluzione

Stai fondendo due caratteristiche completamente distinte.

let mut x; crea un legame mutevole x, permettendoti di modificare ciò a cui x è legato (x = 42) e per i tipi non di riferimento per modificarne il contenuto (x.y = 42).Non controlla la mutabilità del bersaglio di riferimenti.

Questo è diverso dal tipo di riferimenti con cui hai a che fare.

  • &mut T è un riferimento mutabile e può essere utilizzato con la forza *mut T.

  • &T è un riferimento immutabile a cui può essere costretto *const T.

Come vuole la funzione che stai chiamando *mut T, devi passarlo a *mut T o a &mut T; *const T O &T non lo farà.

A dire il vero, puoi solo fare riferimento mutabile a dati mutabili, quindi let x = 42; &mut x non funziona come dovrebbe let mut x invece di let x, ma questo è ancora del tutto distinto e fa parte delle regole di Rust sulla mutabilità.

Altri suggerimenti

La tua funzione si aspetta il puntatore *mut c_int (un puntatore RAW mutabile) e è necessario utilizzare l'operatore &mut per ottenerlo.Tuttavia, è possibile prendere solo il puntatore &mut per le variabili mut, quindi è necessario dichiarare la variabile rank come mut rank.

Se la funzione prevista il puntatore *const c_int, potresti utilizzare &, ma questo non è il caso.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top