0

I am new to Rust. I am trying to implement my own Vec3 toolkit.

I am implementing scalar * vector and vector * scalar operations, my current code

use std::ops::Mul;
use num_traits::real::Real;

#[derive(PartialEq, Debug, Copy, Clone)]
pub struct Vec3<T> (pub T, pub T, pub T);

impl<T: Copy + Clone> Vec3<T> {
    pub fn x(&self) -> T { self.0 }
    pub fn y(&self) -> T { self.1 }
    pub fn z(&self) -> T { self.2 }
}

// Math operation
impl <T: Real> Mul<T> for Vec3<T> {
    type Output = Self;
    fn mul(self, other: T) -> Self::Output {
        Self(self.x() * other, self.y() * other, self.z() * other)
    }
}

fn main() {
    let a = 3.;
    let v = Vec3(1., 2., 3.);
    let result = v * a;
    // this will throw an error
    // let result = a * v;
    println!("{} {} {}", result.0, result.1, result.2)
}

However, currently it only supports vector * scalar. scalar * vector will throw an error.

My question is, how to implement the LHS version of multiplication. I've read this, but it seems that you should call the macro manually for each of f16, f32, f64, etc. But here I want a generic version for Vec3<T>.

I've also tried this for scalar * vector

impl <T: Real> Mul<Vec3<T>> for T {
    type Output = Vec3<T>;
    fn mul(self, other: Vec3<T>) -> Self::Output {
        Vec3(self * other.x(), self * other.y(), self * other.z())
    }
}

But got an error type parameter `T` must be covered by another type when it appears before the first local type (`vec3::Vec3<T>`)

Update

Thanks Chayim Friedman for pointing out why the above workaround is not allowed by the compiler.

However, I still wonder the best way to implement a commutative Mul operator for generic type.

qiuweikang
  • 47
  • 4
  • Simply put you can't implement it that way because someone might want to implement both `Real` and `Mul>` for their type and those would collide with your implementation. See [What exactly is the requirement for "covering" a type & why does a single element tuple satisfy it?](https://stackoverflow.com/questions/75075748/what-exactly-is-the-requirement-for-covering-a-type-why-does-a-single-elemen) for a workaround. – cafce25 May 12 '23 at 05:19
  • 1
    Wow, there was a blog post in This Week In Rust this week about this exactly: https://ohadravid.github.io/posts/2023-05-coherence-and-errors/. – Chayim Friedman May 12 '23 at 09:06

0 Answers0