Skip to content

Rust traits treat (T, &T) and (&T, T) as same type #11384

Closed
@uzytkownik

Description

@uzytkownik

Rust fails for following code:

trait Common<U> {
    fn common<'r, A>(&'r self, f: |&'r U, &'r U| -> A) -> A;
}

impl<'t, T> Common<T> for (T, &'t T) {
    fn common<'r, A>(&'r self, f: |&'r T, &'r T| -> A) -> A {
        f(self.n0_ref(), self.n1_ref().clone())
    }
}

impl<'t, T> Common<T> for (&'t T, T) {
    fn common<'r, A>(&'r self, f: |&'r T, &'r T| -> A) -> A {
        f(self.n0_ref().clone(), self.n1_ref())
    }
}

With message:

testtrait.rs:11:1: 15:2 error: conflicting implementations for trait `Common`
testtrait.rs:11 impl<'t, T> Common<T> for (&'t T, T) {
testtrait.rs:12     fn common<'r, A>(&'r self, f: |&'r T, &'r T| -> A) -> A {
testtrait.rs:13         f(self.n0_ref().clone(), self.n1_ref())
testtrait.rs:14     }
testtrait.rs:15 }
testtrait.rs:5:1: 9:2 note: note conflicting implementation here
testtrait.rs:5 impl<'t, T> Common<T> for (T, &'t T) {
testtrait.rs:6     fn common<'r, A>(&'r self, f: |&'r T, &'r T| -> A) -> A {
testtrait.rs:7         f(self.n0_ref(), self.n1_ref().clone())
testtrait.rs:8     }
testtrait.rs:9 }
testtrait.rs:5:1: 9:2 error: conflicting implementations for trait `Common`
testtrait.rs:5 impl<'t, T> Common<T> for (T, &'t T) {
testtrait.rs:6     fn common<'r, A>(&'r self, f: |&'r T, &'r T| -> A) -> A {
testtrait.rs:7         f(self.n0_ref(), self.n1_ref().clone())
testtrait.rs:8     }
testtrait.rs:9 }
testtrait.rs:11:1: 15:2 note: note conflicting implementation here
testtrait.rs:11 impl<'t, T> Common<T> for (&'t T, T) {
testtrait.rs:12     fn common<'r, A>(&'r self, f: |&'r T, &'r T| -> A) -> A {
testtrait.rs:13         f(self.n0_ref().clone(), self.n1_ref())
testtrait.rs:14     }
testtrait.rs:15 }
error: aborting due to 2 previous errors
task 'rustc' failed at 'explicit failure', /var/tmp/portage-ondisk/portage/dev-lang/rust-9999/work/rust-9999/src/libsyntax/diagnostic.rs:74
task '<main>' failed at 'explicit failure', /var/tmp/portage-ondisk/portage/dev-lang/rust-9999/work/rust-9999/src/librustc/lib.rs:440

However the conflict occurs only when there is T and U such that T = &U and U =&T which means that T = &T - i.e. it is a thing borrowed infinitely many times. As such type is not possible the instances are not conflicting and therefore should be allowed.

Metadata

Metadata

Assignees

No one assigned

    Labels

    E-needs-testCall for participation: An issue has been fixed and does not reproduce, but no test has been added.

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions