Rust關聯類型與默認泛型類型參數
一、關聯類型(associated types)
我們閱讀Rust程式的時候,有時候會出現如下的程式碼:
trait Iterator {
type Item;
fn next(&mut self) -> Option<Self::Item>;
}
下面是上面程式碼的註解:Iterator trait 有一個關聯類型 Item
。Item
是一個佔位類型,同時 next 方法會返回 Option<Self::Item>
類型的值。這個 trait
的實現者會指定 Item
的具體類型。
這裡的type
用法就是關聯類型。
關聯類型(associated types)是一個將類型佔位符與 trait 相關聯的方式,這樣 trait 的方法簽名中就可以使用這些佔位符類型。trait 的實現者會針對特定的實現在這個類型的位置指定相應的具體類型。如此可以定義一個使用多種類型的 trait,直到實現此 trait 時都無需知道這些類型具體是什麼。
使用關聯類型的程式碼示例如下:
pub trait Watch {
type Item;
fn inner(&self) -> Option<Self::Item>;
}
struct A {
data: i32,
}
impl Watch for A {
type Item = i32;
fn inner(&self) -> Option<Self::Item> {
Some(self.data)
}
}
struct B {
data: String,
}
impl Watch for B {
type Item = String;
fn inner(&self) -> Option<Self::Item> {
Some(self.data.clone())
}
}
fn main() {
let a = A{data: 10};
let b = B{data: String::from("B")};
assert_eq!(Some(10), a.inner());
assert_eq!(Some(String::from("B")), b.inner());
}
二、默認泛型類型參數
我們還會碰到如下類型的程式碼:
#[lang = "add"]
pub trait Add<RHS = Self> {
type Output;
#[must_use]
fn add(self, rhs: RHS) -> Self::Output;
}
這裡Add<RHS = Self>
是默認泛型類型參數,表示如果不顯示指定泛型類型,就默認泛型類型為Self
。
當使用泛型類型參數時,可以為泛型指定一個默認的具體類型。如果默認類型就足夠的話,這消除了為具體類型實現 trait 的需要。為泛型類型指定默認類型的語法是在聲明泛型類型時使用 <PlaceholderType=ConcreteType>。
使用默認泛型類型參數的示例程式碼如下:
pub trait Watch<Inner=String> {
type Item;
fn inner(&self) -> Option<Self::Item>;
fn info(&self) -> Inner;
}
struct A {
data: i32,
}
impl Watch<i32> for A {
type Item = i32;
fn inner(&self) -> Option<Self::Item> {
Some(self.data)
}
fn info(&self) -> i32 {
println!("A inner is {}", self.data);
self.data
}
}
struct B {
data: String,
}
impl Watch for B {
type Item = String;
fn inner(&self) -> Option<Self::Item> {
Some(self.data.clone())
}
fn info(&self) -> String {
println!("B inner is {}", self.data);
self.data.clone()
}
}
fn main() {
let a = A{data: 10};
let b = B{data: String::from("B")};
assert_eq!(10, a.info());
assert_eq!(Some(String::from("B")), b.inner());
}