7

I'm trying to understand some code in the D language runtime. It seems like there are separate functions for the following two things:

array1[] += scalar * array2[];
array1[] += array2[] * scalar;

Why can't these be done with one function? I thought multiplication was commutative even in inexact floating-point arithmetic.

mtrw
  • 34,200
  • 7
  • 63
  • 71
dsimcha
  • 67,514
  • 53
  • 213
  • 334

2 Answers2

7

I know nothing about the D language, but I'll happily answer the question in your title:

Is multiplication always commutative in inexact floating point arithmetic?

Up to the "payload" of NaN values, yes. IEEE-754 floating-point multiplication is commutative (and so is addition). If you don't know what the payload of a NaN is, don't worry about it.

Stephen Canon
  • 103,815
  • 19
  • 183
  • 269
  • Even if you don't care about NaN payloads, you still might care that the compiler can't optimize around this... – R.. GitHub STOP HELPING ICE Mar 07 '11 at 17:15
  • 4
    @R..: The 754 standard doesn't actually have any requirements about the payload of a NaN (there are some should clauses, but no shalls), and neither does C99. All a compiler needs to do to be able to optimize around this issue is to not pin down the behavior any further. – Stephen Canon Mar 07 '11 at 17:38
5

I guess the difference is just in the function prototypes - one is (double, double[]) and the other is (double[], double). But the result should be the same either way.

mtrw
  • 34,200
  • 7
  • 63
  • 71
  • But dong array1[] += scalar * array2[]; is rewritten by the compiler as a function call. There's special syntax for these array operations. You don't call the function directly using function call syntax. Why wouldn't the compiler just have one function and rewrite it the same way as array1[] += array2[] * scalar? – dsimcha Feb 15 '11 at 22:44
  • How does the compiler know whether to call `array::operator *(scalar)` or `int::operator *(array)`? Put another way, you need to distinguish between `array1[] += scalar / array2[]` and `array1[] += array2[] / scalar`. So the operator overloading rules must require that both variants be defined. In the case of `*` and `+` the results are the same, but the calling convention is still different. And for `-` and `/`, of course, the results are different too. – mtrw Feb 16 '11 at 02:22
  • But arrays are builtin in D. This is compiler intrinsics, not operator overloading. Also, even with operator overloading, you'd just have one function call the other. You wouldn't have two implementations. – dsimcha Feb 16 '11 at 04:54
  • It doesn't really make sense to promote a scalar to an array, so I still think you need two versions, so that the caller can pass the array and scalar correctly. But certainly it would make sense for one to call the other. – mtrw Feb 16 '11 at 07:11