2016-06-26 13 views
8

मैं इस सरल कोड संकलन करने के लिए कोशिश कर रहा हूँ:जंग समारोह में स्थिर जीवनकाल नहीं है?

fn dox(x: u8) -> u8 { x*2 } 

fn main() { 
    let cb: &'static (Fn(u8) -> u8) = &dox; 
} 

लेकिन यह जंग 1.9 के साथ विफल:

x.rs:4:40: 4:43 error: borrowed value does not live long enough 
x.rs:4  let cb: &'static (Fn(u8) -> u8) = &dox; 
               ^~~ 
note: reference must be valid for the static lifetime... 
x.rs:4:44: 5:2 note: ...but borrowed value is only valid for the block suffix following statement 0 at 4:43 
x.rs:4  let cb: &'static (Fn(u8) -> u8) = &dox; 
x.rs:5 } 
error: aborting due to previous error 

कैसे यह संभव है कि एक नि: शुल्क समारोह स्थिर जीवन भर नहीं है? यह कोड असुरक्षित कैसे हो सकता है?

उत्तर

9

&dox के प्रकार &Fn(u8) -> u8 नहीं है (या यहाँ तक &fn(u8) -> u8), यह महज मजबूर किया हुआ&Fn(u8) -> u8 है। इसलिए, आप वास्तव में एक अस्थायी पते ले रहे हैं। अस्थायी को 'static जीवनकाल में पदोन्नत नहीं किया जाता है, भले ही वे 'static हो। उदाहरण के लिए यह कोड या तो काम नहीं करता है:

fn main() { 
    let a: &'static i32 = &5; 
} 

इसके लिए कुछ कामकाज हैं। आम तौर पर एक बस स्पष्ट रूप से एक static चर बना सकते हैं और उस के संदर्भ ले:

fn main() { 
    static FIVE: i32 = 5; 
    let a: &'static i32 = &FIVE; 
} 

अपने विशिष्ट मामले में कि सीधे काम नहीं करता क्योंकि Fn(u8) -> u8 (, एक विशेषता है विशेष रूप से) एक अनवधि प्रकार है तो आप नहीं कर सकते बस इसे static में रखें। आप ऐसा कर सकते हैं:

fn main() { 
    static DOX: fn(u8) -> u8 = dox; // note: fn, not Fn 
    let a: &'static Fn(u8) -> u8 = &DOX; 
} 

हालांकि, एक Fn* विशेषता वस्तु के लिए एक स्थिर संदर्भ एक नहीं बल्कि मूर्खतापूर्ण बात है। बंद होने वाले 'static संदर्भ बहुत दुर्लभ हैं, इसलिए आप एक सादा fn(u8) -> u8 प्रकार का उपयोग कर सकते हैं और पूरे जीवनकाल व्यवसाय को दूर कर सकते हैं।

संबंधित मुद्दे