Skip to content
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

Simple operator overloading does not work #22743

Closed
gibiansky opened this issue Feb 23, 2015 · 3 comments
Closed

Simple operator overloading does not work #22743

gibiansky opened this issue Feb 23, 2015 · 3 comments
Labels
A-typesystem Area: The type system

Comments

@gibiansky
Copy link

Apologies if this has been covered already or this is the wrong place to file this. This may be a bug or may simply be a lack of documentation, I'm not sure.

I have the following simple code:

use std::ops::Mul;

struct Foo {
    x: f64,
}

impl Mul<Foo> for f64 {
    type Output = Foo;

    fn mul(self, rhs: Foo) -> Foo {
        println!("Multiplying!");
        rhs
    }
}

pub fn main() {
    let f: Foo = Foo { x: 5.0 };
    let val: f64 = 3.0;
    let f2: Foo = val * f;
}

which results in the error message

test.rs:19:25: 19:26 error: mismatched types:
 expected `f64`,
    found `Foo`
(expected f64,
    found struct `Foo`) [E0308]
test.rs:19     let f2: Foo = val * f;
                                   ^
test.rs:19:19: 19:26 error: mismatched types:
 expected `Foo`,
    found `f64`
(expected struct `Foo`,
    found f64) [E0308]
test.rs:19     let f2: Foo = val * f;
                             ^~~~~~~
error: aborting due to 2 previous errors

This usage seems in line with the documentation and the tutorials. It may be related to #21188 and maybe #20749, but I am not sure.

How do I fix this or what am I doing wrong or why is this not working?

Version:

rustc 1.0.0-nightly (2b01a37ec 2015-02-21) (built 2015-02-21)
binary: rustc
commit-hash: 2b01a37ec38db9301239f0c0abcf3c695055b0ff
commit-date: 2015-02-21
build-date: 2015-02-21
host: x86_64-apple-darwin
release: 1.0.0-nightly
@bombless
Copy link
Contributor

Seems to be a bug, this code works

use std::ops::Mul;

pub struct Foo {
    x: f64,
}

impl Mul<Foo> for f64 {
    type Output = Foo;

    fn mul(self, rhs: Foo) -> Foo {
        println!("Multiplying!");
        rhs
    }
}

pub fn main() {
    let f: Foo = Foo { x: 5.0 };
    let val: f64 = 3.0;
    let f2: Foo = Mul::mul(val, f);
}

@gibiansky
Copy link
Author

Yup, looks like that works, so looks like some sort of error in the desugaring...

@Aatch
Copy link
Contributor

Aatch commented Feb 24, 2015

Just FYI, operator overloading isn't actually desguared, since desugaring happens before typechecking and we don't know if it's an overloaded operator until after then.

Anyway, looks like this is a bug if the type checking for operations on primitive types. I think the fix is actually #19434, which was closed while #20749 was being resolved. Seeing as that issue has now been resolved, this bug may be fixable. I don't know enough details to be sure (specifically, whether or not this bug is indeed fixable, though the fact that implementation is valid suggests that it is).

@japaric @nikomatsakis?

@Aatch Aatch added the A-typesystem Area: The type system label Feb 24, 2015
nikomatsakis added a commit to nikomatsakis/rust that referenced this issue Mar 25, 2015
Fixes rust-lang#22743.
Fixes rust-lang#19035.
Fixes rust-lang#22099.

(Those all seem to be exactly the same scenario.)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
A-typesystem Area: The type system
Projects
None yet
3 participants