Nicer syntax for lifetime arguments?


#1

Currently if you have multiple lifetimes with restrictions, the impl will not require you to restate these restrictions, but it does require you to explicit every lifetime argument everywhere:

struct S<'a, 'b: 'a + 'c, 'c: 'a> {
    x: X<'a, 'b, 'c>,
}

impl<'a, 'b, 'c> S<'a, 'b, 'c> {
    fn new(x: X<'a, 'b, 'c>) -> S<'a, 'b, 'c> {
        S { x }
    }
}

As every lifetime for S could be inferred from X’s, I feel that the compiler should accept something along the lines of:

struct S<'a, 'b: 'a + 'c, 'c: 'a> {
    x: X<'a, 'b, 'c>,
}

impl<'a, 'b, 'c> S<'a, 'b, 'c> {
    fn new(x: X<'a, 'b, 'c>) -> S {
        S { x }
    }
}

Thoughts?


#2

Under two of the proposed RFCs – one of which infers the 'a + 'c and one of which makes explicit <'a> binders unnecessary outside of functions – your example would become:

struct S<'a, 'b, 'c> {
    x: X<'a, 'b, 'c>,
}

impl S<'a, 'b, 'c> {
    fn new(x: X<'a, 'b, 'c>) -> S<'a, 'b, 'c> {
        S { x }
    }
}

You can also change to fn new(x: X<'a, 'b, 'c>) -> Self, which is probably what I would actually write.

Note that I would also like to introduce conventions (enforced by lint, ideally) that any region name which cross binding levels must be “meaningful” – since that is hard to quantify, the lint would probably just check that they are more than one letter =).