rust-lang / rust-lang/rfcs

Commutative multiplication and addition

Open
#2,608 18 comments 8 reactions 0 assignees View on GitHub

Nobody has claimed this yet.

Dominant language
Markdown
Stars
6.6k
Forks
1.7k
Avg merge
16h 14m
Merged PRs (30d)
1

Description

I was surprised to learn that the implementation of core::ops::{Add, Mul} (keywords: addition, multiplication) is not automatically (and exclusively) commutative. This is often not a problem for cases where it is possible to both impl Mul<X> for Y and impl Mul<Y> for X, but this is not an option when generics are involved.

For example, this implementation of Mul allows multiplying Size by any basic number type (from num_traits), as in Size(12) * 2 or Size(42) * 1.0:

impl<T, U> Mul<U> for &Size<T>
where
    T: ToPrimitive,
    U: ToPrimitive
{
    type Output = Size<u64>;

    fn mul(self, other: U) -> Self::Output {
        // omitted
    }
}

but it is not possible to define an ergonomic and efficient inverse to support the commutative variant of the same operations (2 * Size(12) or 3.0 * Size(7)), because the following is illegal:

impl<T> Mul<Size<T>> for ToPrimitive
where
    T: ToPrimitive,
{
    type Output = Size<u64>;

    fn mul(self, other: Size<T>) -> Self::Output {
        Size::Bytes((self as u64 * other.bytes()) as u64)
    }
}

as the self parameter to the mul function results in an attempt to define a non-generic parameter with unknown size.

I would like to use this issue to sound out ideas to support commutative operations, at the very least for operations that are typically (read: mathematically) commutative, but would appreciate any insight or commentary that sheds light on anything I'm missing here first.

Contributor guide

No contributing guide indexed for this repository

First steps

  1. Read the whole issue, then the project's contributing guide.
  2. Comment on the issue to say you are picking it up — it saves two people doing the same work.
  3. Fork the repository and make your change on a branch.
  4. Open a pull request that references the issue number.

Research direction

Start by reading the issue's discussion of core::ops::{Add, Mul}, including the generic Size and ToPrimitive examples, then review the existing comments for proposed approaches. A complete contribution would need a settled design for supporting commutative operations and agreement on whether it should proceed through the Rust RFC process.

Written by the indexing model from the issue text.

Assessment

Tech stack
rust
Domain
compilers
Issue type
Feature
Difficulty
5/5
Estimated time
Over a week
Activity status
Stale
Clarity
Needs clarification
Newbie friendliness
25/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.