Join GitHub today
GitHub is home to over 31 million developers working together to host and review code, manage projects, and build software together.
Sign upInherent trait implementations #1880
Comments
This comment has been minimized.
This comment has been minimized.
|
Please explain what happens when calling crate A {
struct PointType {
x: f32,
y: f32,
}
}
crate B {
trait OnePointTrait {
fn a(&self) -> f32;
fn b(&self) -> f32;
}
exposed impl OnePointTrait for PointType {
fn a(&self) -> f32 { self.x }
fn b(&self) -> f32 { self.y }
}
}
crate C {
trait OtherPointTrait {
fn a(&self) -> f32;
fn b(&self) -> f32;
}
exposed impl OtherPointTrait for PointType {
fn a(&self) -> f32 { self.y }
fn b(&self) -> f32 { self.x }
}
} |
This comment has been minimized.
This comment has been minimized.
|
Could add a restriction such that On a side note, this could also help out the 'num-traits' crate which IIRC reexports all the trait impls in the 'num' crate. |
This comment has been minimized.
This comment has been minimized.
|
You can always put all the traits into one module and do Also, advanced enough IDEs (or rustfix) will be able to automatically insert the necessary imports (I'm working on this at this very moment) |
This comment has been minimized.
This comment has been minimized.
|
The correct term here, IMO, is "inherent", and this would have to obey the rules of inherent impls. |
This comment has been minimized.
This comment has been minimized.
|
Agree that "inherent" is the correct term. One way to think of this feature is syntactic sugar to generate an |
This comment has been minimized.
This comment has been minimized.
Wopple
commented
Feb 1, 2017
•
|
IMO, the extra effort of having to write an additional import is worth the flexibility of being able to define your own implementations of functions. I can imagine a case where you want to use a struct but you don't like the implementation of a trait provided by the crate. If that implementation was inherent, how would you opt out of using it in favor of an implementation with the same signature of your choosing? Edit: never mind (see below) |
This comment has been minimized.
This comment has been minimized.
I'm not sure how this idea makes your concern any worse. e.g. It's already possible for |
This comment has been minimized.
This comment has been minimized.
|
Inherit impls actually came up when discussing "thin" pointers to traits. One idea (that I liked) was to allow structs to declare which traits they must implement: struct MyStruct: Trait1 + Trait2 + Trait3; // or struct MyStruct impl Trait1 ...This would have two side effects (not including thin pointer stuff).
The nice thing about this alternative is that it keeps everything in one place. |
This comment has been minimized.
This comment has been minimized.
|
@Stebalien This is an OK alternative, but it seems a bit redundant with the |
This comment has been minimized.
This comment has been minimized.
burdges
commented
Feb 1, 2017
•
|
I'd think the syntax for your
or maybe Now |
This comment has been minimized.
This comment has been minimized.
Wopple
commented
Feb 1, 2017
•
|
@frewsxcv In the following example, it prints 0 or 1 depending on which trait you import: struct MyStruct {
val: u32
}
trait Trait1 {
fn get_val(&self) -> u32;
}
trait Trait2 {
fn get_val(&self) -> u32;
}
impl Trait1 for MyStruct {
fn get_val(&self) -> u32 { self.val }
}
impl Trait2 for MyStruct {
fn get_val(&self) -> u32 { self.val + 1 }
}
mod test {
use ::MyStruct;
// use ::Trait1;
use ::Trait2;
fn run() {
let s = MyStruct { val: 0 };
println!("val: {:?}", s.get_val());
}
}it can't compile if you import both because the |
This comment has been minimized.
This comment has been minimized.
|
@Wopple You can differentiate via: Trait1::get_val(&s)EDIT: I originally wrote this, but it's wrong: (s as Trait1).get_val() |
This comment has been minimized.
This comment has been minimized.
Wopple
commented
Feb 2, 2017
|
@frewsxcv I see, thanks! |
This comment has been minimized.
This comment has been minimized.
|
Perhaps something like |
This comment has been minimized.
This comment has been minimized.
|
Also, |
This comment has been minimized.
This comment has been minimized.
ideasman42
commented
Feb 8, 2017
•
|
One of the down-sides to the current situation (needing to explicitly |
This comment has been minimized.
This comment has been minimized.
Hmm... I can see why it would be annoying having to find the correct trait, but I have never found this to be an excessive "hassle" before... at least, not to the degree that I would rather not use traits. Could you give an example of where this was a huge burden? |
frewsxcv
changed the title
Idea: Exposed trait implementations
Idea: Inherent trait implementations
Sep 4, 2017
frewsxcv
changed the title
Idea: Inherent trait implementations
Inherent trait implementations
Sep 4, 2017
This comment has been minimized.
This comment has been minimized.
newpavlov
commented
Oct 13, 2017
•
|
I would love to see this feature implemented, as for example in the RustCrypto I have to re-export traits in every crate to make it more convenient for users, or otherwise they'll have to list additional crate (containing traits) as explicit dependency. Also it makes harder to write documentation, as I have to explain how traits are organized to users who do not want to write generic code and just want to call several methods and have stuff done. Overall it's a very annoying papercut for crate authors and users. |
This comment has been minimized.
This comment has been minimized.
burdges
commented
Oct 13, 2017
|
It's never been clear to me why RustCrypto uses so many crates instead of features. Yes, crates provide an easier to understand separation, but if the crates all reside in the same repository anyways then most advantages seem moot. There is no shortage of applications for this language feature though of course, so I'm not objecting to anything. :) We rand into issues when discussing |
This comment has been minimized.
This comment has been minimized.
|
I would like to see this feature too: I'm currently looking at generating traits and types from javascript IDL files, and I have to choose between generating inherent methods vs trait methods for interfaces, and neither corresponds cleanly to what the javascript API actually looks like. |
Centril
added
the
T-lang
label
Jan 21, 2018
newpavlov
referenced a pull request that will
close
this issue
Mar 27, 2018
Open
RFC: inherent trait implementation #2375
stepancheg
referenced this issue
Oct 24, 2018
Open
Make most of Message functions non-virtual to reduce generated code size #339
This comment has been minimized.
This comment has been minimized.
stepancheg
commented
Oct 24, 2018
|
I want to point to (now closed) "custom prelude" RFC #890 Should that RFC implemented, the described problem could be solved with a custom prelude: the client could import |
This comment has been minimized.
This comment has been minimized.
idanarye
commented
Oct 28, 2018
|
If I could add my suggestion, I would like to see a syntax like this: impl PointTrait for PointType {
fn x(&self) -> f32 { self.x }
pub fn y(&self) -> f32 { self.y }
}You'd have to The advantages of marking the specific function rather then the impl statement are:
|
This comment has been minimized.
This comment has been minimized.
idanarye
commented
Oct 31, 2018
|
I've implemented my syntax with a |
frewsxcv commentedFeb 1, 2017
I've been working a lot with traits lately with this rust-geo pull request.
In that pull request, it splits up concrete geospatial types and geospatial operations. A simplified example:
Now, if someone ever wanted to use this, they'd have to import both the type and the trait:
Most of the time, the user is always going to want the associated methods associated with
PointType, so it's a little unfortunate that the user has to add another import whenever they want this functionality.It'd be cool if I could make a trait implementation as
exposedso that the triat methods are always available on that specific type. Something like:(There's probably a better keyword to use here than
exposed, or maybe some other way to indicate this.)Then the user can just do:
I haven't thought too long about this, so I might be overlooking something here. I don't feel strongly at all about this, just expressing a thought.