2016-05-16 154 views
2

我無法瞭解關聯的類型。我的問題代碼:實現具有相關特徵類型的特徵

trait Fooer { 
    fn foo(&self); 
} 

trait FooStore { 
    type T: Fooer; 
    fn store_foo(&self, fooer: Self::T); 
} 

#[allow(dead_code)] 
struct DB {} 

impl FooStore for DB { 
    type T = Fooer; 

    fn store_foo(&self, _fooer: Self::T) {} 
} 

fn main() {} 

Play link

這裏的目的是使用相關的類型,使FooStore特質不需要的impl<F:Fooer, T: FooStore<F>> FooStore<F> for DB的尷尬和問題的語法,因爲經常抱怨F不被使用。

但是,此功能上的official docs顯示實現基礎關聯類型的對象 - 但不是特徵。在這個例子中,DB不知道哪些結構可能被傳入store_foo(..),所以它需要使用特徵來解決這個問題。

說了這麼多,在impl期間,如何獲得關聯類型以使用特徵?也就是說,我怎麼寫type T = Fooer;?或者我以某種方式使用這個錯誤?

注意:我在構建這個示例時遇到了一些麻煩,現在我試圖糾正這個問題。我有錯誤是:

cargo: the trait `Fooer` cannot be made into an object [E0038] 

回答

3

這裏的目的是使用相關的類型,使FooStore特質不需要的impl<F:Fooer, T: FooStore<F>> FooStore<F> for DB的尷尬和問題的語法,因爲經常抱怨F不被使用。

您的結構DB需要指定實施FooerFooStore::T的具體類型。 Fooer是一個特徵,但也可以用作未分類的類型。但是,這裏不能使用未定義的類型,因爲您無法按值傳遞未定義類型的參數(其中FooStore::store_foo要求)。

如果您不希望DBFooStore::T指定特定類型,則可以使DB爲通用。

use std::marker::PhantomData; 

#[allow(dead_code)] 
struct DB<F: Fooer> { 
    _phantom: PhantomData<F>, 
} 

impl<F: Fooer> FooStore for DB<F> { 
    type T = F; 

    fn store_foo(&self, _fooer: Self::T) {} 
} 

注意使用PhantomData:我們用它來強制參數使用T,它也預示着DB<T>概念擁有T類型的對象。