Skip to content

E0308 because Self is not equivalent to concrete type in constructor (lifetime mismatch) #70265

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
PieterPenninckx opened this issue Mar 22, 2020 · 5 comments
Labels
C-bug Category: This is a bug.

Comments

@PieterPenninckx
Copy link
Contributor

PieterPenninckx commented Mar 22, 2020

I tried this code:

struct S<'a> {
    x: &'a str
}

impl S<'static> {
    fn f(self) {}
}

impl<'a> S<'a> {
    fn f1() -> S<'static> {
        Self{x: ""} // error[E0308]: mismatched types
    }
    fn f2() -> S<'static> {
        S{x: ""}
    }
    
    fn g1() {
        S::f(Self{x: ""}) // error[E0308]: mismatched types
    }
    fn g2() {
        S::f(S{x: ""})
    }
}

fn main() {}

I expect this code to compile without error because I would assume that Self is equivalent to S in this case. I expect this equivalence because Self is used as an alias of S in the body of a function and lifetimes cannot be annotated in function bodies (edit: this turns out to be incorrect, see below).

Instead, this happened:

error[E0308]: mismatched types
  --> test.rs:11:9
   |
11 |         Self{x: ""} // error[E0308]: mismatched types
   |         ^^^^^^^^^^^ lifetime mismatch
   |
   = note: expected struct `S<'static>`
              found struct `S<'a>`
note: the lifetime `'a` as defined on the impl at 9:6...
  --> test.rs:9:6
   |
9  | impl<'a> S<'a> {
   |      ^^
   = note: ...does not necessarily outlive the static lifetime

error[E0308]: mismatched types
  --> test.rs:18:14
   |
18 |         S::f(Self{x: ""}) // error[E0308]: mismatched types
   |              ^^^^^^^^^^^ lifetime mismatch
   |
   = note: expected struct `S<'static>`
              found struct `S<'a>`
note: the lifetime `'a` as defined on the impl at 9:6...
  --> test.rs:9:6
   |
9  | impl<'a> S<'a> {
   |      ^^
   = note: ...does not necessarily outlive the static lifetime

error: aborting due to 2 previous errors

For more information about this error, try `rustc --explain E0308`.

Meta

rustc --version --verbose:

rustc 1.42.0 (b8cedc004 2020-03-09)
binary: rustc
commit-hash: b8cedc00407a4c56a3bda1ed605c6fc166655447
commit-date: 2020-03-09
host: x86_64-unknown-linux-gnu
release: 1.42.0
LLVM version: 9.0

Same behaviour with the nightly version of Rust:

rustc 1.44.0-nightly (1057dc97a 2020-03-20)
binary: rustc
commit-hash: 1057dc97afce39ff6a224966ece3ed438af4c1f5
commit-date: 2020-03-20
host: x86_64-unknown-linux-gnu
release: 1.44.0-nightly
LLVM version: 9.0

Probably related to: #69224

@PieterPenninckx PieterPenninckx added the C-bug Category: This is a bug. label Mar 22, 2020
@tesuji
Copy link
Contributor

tesuji commented Mar 22, 2020

The error is legit and right.

@tesuji
Copy link
Contributor

tesuji commented Mar 22, 2020

Self is not the same as type name.

@tesuji
Copy link
Contributor

tesuji commented Mar 22, 2020

In the impl block, Self is alias for S<'a>, not S alone.
Anyway, this maybe a duplicate of #66176.

@jonas-schievink
Copy link
Contributor

Yeah, this is working as intended, so closing.

@PieterPenninckx
Copy link
Contributor Author

For people reading this in the future: in contrast to what I initially believed, lifetimes can be annotated in function bodies (at least in certain cases), as illustrated in the following code which compiles:

struct S<'a> { x: &'a str }

impl S<'static> { fn f(self) {} }

impl<'a> S<'a> {
    fn f2() -> S<'static> {
        S::<'static>{x: ""} // Lifetime annotation in function body
    }
  
    fn g2() {
        S::f(S::<'static>{x: ""})  // Lifetime annotation in function body
    }
}

fn main() {}

With this knowledge, the error indeed makes sense to me.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
C-bug Category: This is a bug.
Projects
None yet
Development

No branches or pull requests

3 participants