rust-num / num-derive

Procedural macros to derive numeric traits in Rust
Apache License 2.0
166 stars 24 forks source link

Provide macro derive for CheckedAdd, CheckedSub, etc. #25

Open esoterra opened 5 years ago

esoterra commented 5 years ago

I would like to be able to derive the traits for CheckedAdd, CheckedSub, and the other checked arithmetic for structs whose members implement those traits.

A simple solution would be to generate impl blocks that look something like the following.

struct Position {
   x: u32,
   y: u32
}

impl CheckedSub for Position { 
   fn checked_sub(&self, v: &Self) -> Option<Self> {
      match ( self.x.checked_sub(v.x), self.y.checked_sub(v.y) ) {
         (Some(x), Some(y)) => Some( Position { x, y } ),
         _ => None
      } 
   }
}

I had initially suggested this be added to derive_more, but the owner has indicated that derive_more is meant to provide support for std traits not traits from crates like num-traits. https://github.com/JelteF/derive_more/issues/77

cuviper commented 5 years ago

We have the num-derive crate for stuff like this -- I'll see if I can transfer this issue.

However, while this is simple enough for newtype wrappers of a single field, it's questionable with multiple fields. We don't really know in general that element-wise operations are correct, versus some other approach. For instance, CheckedMul may want to be more like a cross product instead of multiplying each element.

esoterra commented 5 years ago

Thanks for transferring the issue. I think that element-wise behavior is intuitive for add-like and subtract-like operations, but agree that multiply and divide might imply other semantics.