Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Double dispatch on arithmetic & relational operations for number type…
…s. (#377) This PR uses the existing single-dispatch mechanism to implement arithmetic & relational operators with double dispatch. As a result we don't typically need to convert between number types. For instance, if you add a `Nat` and an `Int` you get an `Int` as a result. The goal is to always return the correct value or result according to mathematics, so there is no danger of overflow or unexpected results. The output type is chosen so that it is large enough to represent the outcome, e.g. adding two `I64` will result in an `Int`, not an `I64`. Dividing two integers results in a rational number (`Rat`). Floats are inexact, so when you have an operation using floats (`F32` or `F64`) you will always get a float as a result. How double dispatch is implemented via single dispatch: The idea is to turn a method on the top argument into a distinct method on the second argument based on the top argument's type. If you look in `std.number` you'll see how this was achieved. When calling `Int.+`, it pushes the top number onto the `int` stack label and calls the `int+` method on the second argument. When calling `Nat.+`, it pushes the top number onto the `nat` stack label and calls the `nat+` method on the second argument. Thus if you have a type implement `int+` and `nat+` it can adjust the return types based on the value. In addition, this PR also: - Moves the number methods from `std.prelude` to `std.number`. You don't need to import `std.number` directly. - Adds a number type `Zero` which represents only the number 0. - Adds a rational number type `Rat`. - Adds a complex number type `Complex(a,b)`, parametrized on the types for the real and imaginary components. - Merges `USize` and `ISize` types as `Size`. - Merges `UOffset` and `IOffset` types as `Offset`. - Removes `UIndex`. - Changes the types in std.posix to take advantage of resources a bit better, and allow for error handling. - Changes `==` to `=` (but `==` still works).
- Loading branch information