Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to specify a lifetime for an Option<closure>?

I'm trying to put a field on a struct that should hold an Option<closure>.

However, Rust is yelling at me that I have to specify the lifetime (not that I would have really grokked that yet). I'm trying my best to do so but Rust is never happy with what I come up with. Take a look at my inline comments for the compile errors I got.

struct Floor{
    handler: Option<|| ->&str> //this gives: missing lifetime specifier 
    //handler: Option<||: 'a> // this gives: use of undeclared lifetime name `'a`
}

impl Floor {
    // I guess I need to specify life time here as well 
    // but I can't figure out for the life of me what's the correct syntax
    fn get(&mut self, handler: || -> &str){
        self.handler = Some(handler);
    }
}
like image 212
Christoph Avatar asked May 25 '14 20:05

Christoph


1 Answers

This gets a bit trickier.

As a general rule of thumb, whenever you're storing a borrowed reference (i.e., an & type) in a data structure, then you need to name its lifetime. In this case, you were on the right track by using a 'a, but that 'a has to be introduced in the current scope. It's done the same way you introduce type variables. So to define your Floor struct:

struct Floor<'a> {
    handler: Option<|| -> &'a str>
}

But there's another problem here. The closure itself is also a reference with a lifetime, which also must be named. So there are two different lifetimes at play here! Try this:

struct Floor<'cl, 'a> {
    handler: Option<||:'cl -> &'a str>
}

For your impl Floor, you also need to introduce these lifetimes into scope:

impl<'cl, 'a> Floor<'cl, 'a> {
    fn get(&mut self, handler: ||:'cl -> &'a str){
        self.handler = Some(handler);
    }
}

You could technically reduce this down to one lifetime and use ||:'a -> &'a str, but this implies that the &str returned always has the same lifetime as the closure itself, which I think is a bad assumption to make.

like image 129
BurntSushi5 Avatar answered Oct 01 '22 16:10

BurntSushi5