2014-09-21 17 views
18

Editor's note: This code no longer produces the same error after RFC 599 was implemented, but the concepts discussed in the answers are still valid.爲什麼在框架<T>中需要「明確的生存期限」?

我試圖編譯這段代碼:

trait A { 
    fn f(&self); 
} 

struct S { 
    a: Box<A>, 
} 

,我得到這個錯誤:

a.rs:6:13: 6:14 error: explicit lifetime bound required 
a.rs:6  a: Box<A>, 

我想S.a自己的A一個實例,也不要看看這個生命在這裏是多麼適合。我需要做什麼才能使編譯器高興?

我防鏽版本:

rustc --version 
rustc 0.12.0-pre-nightly (79a5448f4 2014-09-13 20:36:02 +0000) 

回答

16

這裏的問題是,一個特徵可以參考實現,所以,如果你不指定任何盒的所需的壽命可以存儲在那裏。

您可以在此rfc中查看有關使用期限的要求。

所以一個可能的解決方案是將壽命綁定所以Send(我們把我在S):

trait A { 
    fn f(&self); 
} 

struct I; 

impl A for I { 
    fn f(&self) { 
     println!("A for I") 
    } 
} 

struct S { 
    a: Box<A + Send> 
} 

fn main() { 
    let s = S { 
     a: box I 
    }; 
    s.a.f(); 
} 

另一種是設置生存期,以'a(我們可以把一個參考& I或I至S ):

trait A { 
    fn f(&self); 
} 

struct I; 

impl A for I { 
    fn f(&self) { 
     println!("A for I") 
    } 
} 

impl <'a> A for &'a I { 
    fn f(&self) { 
     println!("A for &I") 
    } 
} 

struct S<'a> { 
    a: Box<A + 'a> 
} 

fn main() { 
    let s = S { 
     a: box &I 
    }; 
    s.a.f(); 
} 

注意,這是更普遍的,我們可以同時存儲引用和所擁有的數據(Send那種有'static一生),但你需要一輩子parame在任何地方使用類型。

+0

感謝您的RFC鏈接,它確實揭示了Boxes內部的生命週期。 – 2014-09-22 03:14:45

18

(略迂腐一點:A是一個性狀,所以S不擁有的A一個例如,可以擁有一個包裝實例某種類型的實現A。)

甲性狀對象表示具有某種未知類型的數據,也就是說,唯一知道的數據是它實現了特徵A。由於類型未知,因此編譯器無法直接推斷所包含數據的生命週期,因此需要在特徵對象類型中明確說明此信息。

這是通過Trait+'lifetime完成的。最簡單的途徑是隻使用'static,即,完全禁止存儲數據,可以由於範圍成爲無效:

a: Box<A + 'static> 

此前,(前壽命有界性狀的可能性的對象和被引入此explicit lifetime bound required錯誤消息)所有盒裝特質對象都是隱含的'static,也就是說,這種限制形式是唯一的選擇。

最靈活的形式被暴露在外部的壽命:

struct S<'x> { 
    a: Box<A + 'x> 
} 

這允許S存儲實現A,可能具有在其中的S是有效的範圍的一些限制的任何類型的特徵的對象(即對於'x小於'static的對象,S對象將被困在某個堆棧幀內)。

相關問題