# Rework operator interfaces

<!--
Part of the Carbon Language project, under the Apache License v2.0 with LLVM
Exceptions. See /LICENSE for license information.
SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
-->

[Pull request](https://github.com/carbon-language/carbon-lang/pull/1178)

<!-- toc -->

## Table of contents

-   [Problem](#problem)
-   [Background](#background)
-   [Proposal](#proposal)
-   [Details](#details)
-   [Rationale](#rationale)
-   [Alternatives considered](#alternatives-considered)
    -   [Use `ComparableWith` instead of `OrderedWith`](#use-comparablewith-instead-of-orderedwith)

<!-- tocstop -->

## Problem

Our operator interface names need to be updated to match the decision in
[#1058](https://github.com/carbon-language/carbon-lang/issues/1058). Further, we
are missing a description of the interfaces used to overload comparison
operators, and the rules are not up to date with the decision in
[#710](https://github.com/carbon-language/carbon-lang/issues/710).

## Background

See the two leads issues for background and discussion of options.

## Proposal

See changes to the design.

## Details

Beyond establishing names for interfaces, this proposal also establishes:

-   We will have high-level interfaces for equality and relational comparison.
    The equality interface provides both `==` and `!=`. The relational
    comparison interface provides all of `<`, `<=`, `>`, and `>=`.
-   Following the convention established for arithmetic operators, we provide
    both a heterogeneous comparison interface and a homogeneous constraint. For
    example, `T is EqWith(T)` is equivalent to `T is Eq`.
-   The high-level interfaces always return `bool`.
-   The high-level interfaces have expected semantics associated with them.

It is intended that we also provide low-level interfaces, to directly control
individual operators and to allow a result type other than `bool`. These are not
included in this proposal, as it's not yet clear how they should be specified,
and it's more important to get the high-level interfaces decided at this point.

## Rationale

-   [Language tools and ecosystem](/docs/project/goals.md#language-tools-and-ecosystem)
    -   High-level semantics allow tools to reason about the intended meaning of
        Carbon code. For example, a tool could statically or dynamically
        determine that an implementation of `Ordered` doesn't satisfy the
        expected rules and produce a warning.
-   [Performance-critical software](/docs/project/goals.md#performance-critical-software)
    -   We expect `==` and ordering to be customized separately, in order to
        avoid cases where a suboptimal `==` is constructed in terms of an
        ordering. See
        [C++ committee paper P1190R0](http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2018/p1190r0.html)
        for details on the problem.
-   [Code that is easy to read, understand, and write](/docs/project/goals.md#code-that-is-easy-to-read-understand-and-write)
    -   Combining all comparison operators of the same kind -- equality or
        relational -- into a single interface makes it both easier to implement
        them and easier to write a generic constraint for them. This approach is
        also expected to be easy to teach, with the low-level interfaces only
        explained to a more advanced audience.
-   [Practical safety and testing mechanisms](/docs/project/goals.md#practical-safety-and-testing-mechanisms)
    -   While there are rules for the comparison interfaces, violating those
        rules does not result in immediate unbounded undefined behavior.
        However, implementations should still attempt to detect violations of
        these rules and report them where that is feasible.
-   [Interoperability with and migration from existing C++ code](/docs/project/goals.md#interoperability-with-and-migration-from-existing-c-code)
    -   The intent to provide a low-level interface for individual operators is
        directly motivated by the desire to provide strong interoperability with
        operators defined in C++. While this functionality is not part of this
        proposal, it's expected to follow once the interactions with generics
        are worked out.

## Alternatives considered

### Use `ComparableWith` instead of `OrderedWith`

We could use the term "comparable" for relational comparisons instead of
"ordered". There is existing practice for both: for example, Rust and Haskell
use `Ord`, and Swift uses `Comparable`.

The main argument for using "ordered" instead of "comparable" is that `==` and
`!=` are also a form of comparison but aren't part of `OrderedWith`, and the
word "ordered" distinguishes relational comparison from equality comparison.
