W3Cschool
恭喜您成為首批注冊用戶
獲得88經(jīng)驗值獎勵
Rust 在標(biāo)準(zhǔn)庫有許多不同的智能指針類型,但是有兩種特別的類型。Rust 的安全來自于編譯時檢查,但原始指針沒有這樣的保證,使用起來不安全?! ?/p>
*const T 和 *mut T 在 Rust 中被稱為“原始指針”。有時,當(dāng)寫庫的某些類型時,出于某種原因你需要繞過 Rust 的安全保證。在這種情況下,你可以使用原始指針來實現(xiàn)你的庫,同時為給用戶一個安全接口。例如,允許 * 指針起別名,允許他們被用來寫共享類型,甚至線程安全共享內(nèi)存類型( Rc和 Arc 類型在 Rust 中都被完全實現(xiàn))。
這里要記住原始指針與其他指針類型是不同的地方。他們:
創(chuàng)建一個原始指針是絕對安全的:
let x = 5;
let raw = &x as *const i32;
let mut y = 10;
let raw_mut = &mut y as *mut i32;
然而,非關(guān)聯(lián)化的指針是不安全的。這是行不通的:
let x = 5;
let raw = &x as *const i32;
println!("raw points at {}", *raw);
它會給出這樣的錯誤:
error: dereference of unsafe pointer requires unsafe function or block [E0133]
println!("raw points at{}", *raw);
^~~~
原始指針廢棄時,你承擔(dān)這樣的后果,那就是它不指向那個正確的地方。因此,你需要 unsafe:
let x = 5;
let raw = &x as *const i32;
let points_at = unsafe { *raw };
println!("raw points at {}", points_at);
要了解更多關(guān)于原指針的操作,請看 API 文檔。
對 FFI 來說原指針是很有用的:Rust 的 *const T 和 *mut T 與 C 的 const T 和 T 是相似的。更多關(guān)于它的使用,請看 FFI 章節(jié)。
在運行時,一個原始指針 * 和一個指向同一塊數(shù)據(jù)的引用具有相同的表示。事實上,一個 &T 引用將隱式強制轉(zhuǎn)換為安全代碼中的 *const T 原始指針并且與常量 mut 相似(兩種強制轉(zhuǎn)換可以顯式地被執(zhí)行,值分別是 const T 和 mut T)?! ?/p>
相反,從 const 指向引用 & 是不安全的。 &T 總是有效的,因此至少,原始指針 const T 必須指向一個 T 類型的有效實例。此外,由此產(chǎn)生的指針必須滿足引用的別名使用和可變性規(guī)則。編譯器假定這些屬性對任何引用都是真的,不管他們是如何創(chuàng)建的,因此任何從原始指針的轉(zhuǎn)換都認為它們有這些屬性。程序員必須保證這一點?! ?/p>
推薦的轉(zhuǎn)換方法是
let i: u32 = 1;
// explicit cast
let p_imm: *const u32 = &i as *const u32;
let mut m: u32 = 2;
// implicit coercion
let p_mut: *mut u32 = &mut m;
unsafe {
let ref_imm: &u32 = &*p_imm;
let ref_mut: &mut u32 = &mut *p_mut;
}
&*x 解除引用要使用 transmute。transmute 是非常強大的,更受限制的操作也能正確使用;例如,它要求 x 是一個指針(而不像 transmute)。
Copyright©2021 w3cschool編程獅|閩ICP備15016281號-3|閩公網(wǎng)安備35020302033924號
違法和不良信息舉報電話:173-0602-2364|舉報郵箱:jubao@eeedong.com
掃描二維碼
下載編程獅App
編程獅公眾號
聯(lián)系方式:
更多建議: