]> Cypherpunks repositories - gostls13.git/commitdiff
spec: add section on comparable constraint
authorRobert Griesemer <gri@golang.org>
Fri, 28 Jan 2022 23:34:40 +0000 (15:34 -0800)
committerRobert Griesemer <gri@golang.org>
Tue, 1 Feb 2022 15:39:16 +0000 (15:39 +0000)
For #50646.
Fixes #50791.

Change-Id: I8fec25ae3f0280c5b5a778011d23842b886ba79e
Reviewed-on: https://go-review.googlesource.com/c/go/+/381896
Trust: Robert Griesemer <gri@golang.org>
Reviewed-by: Ian Lance Taylor <iant@golang.org>
doc/go_spec.html

index c653cbffc0274b0781f15ad809382badbcfabe9f..69ac1d353fa06dced892832c237863fdbe98cf1f 100644 (file)
@@ -1,6 +1,6 @@
 <!--{
        "Title": "The Go Programming Language Specification - Go 1.18 Draft (incomplete)",
-       "Subtitle": "Version of Jan 28, 2022",
+       "Subtitle": "Version of Jan 31, 2022",
        "Path": "/ref/spec"
 }-->
 
@@ -2656,6 +2656,53 @@ may be omitted for convenience:
 type Constraint ~int               // illegal: ~int is not inside a type parameter list
 </pre>
 
+<!--
+We should be able to simplify the rules for comparable or delegate some of them
+elsewhere once we have a section that clearly defines how interfaces implement
+other interfaces based on their type sets. But this should get us going for now.
+-->
+
+<p>
+The <a href="#Predeclared_identifiers">predeclared</a>
+<a href="#Interface_types">interface type</a> <code>comparable</code>
+denotes the set of all concrete (non-interface) types that are
+<a href="#Comparison_operators">comparable</a>. Specifically,
+a type <code>T</code> implements <code>comparable</code> if:
+</p>
+
+<ul>
+<li>
+       <code>T</code> is not an interface type and <code>T</code> supports the operations
+       <code>==</code> and <code>!=</code>; or
+</li>
+<li>
+       <code>T</code> is an interface type and each type in <code>T</code>'s
+       <a href="#Interface_types">type set</a> implements <code>comparable</code>.
+</li>
+</ul>
+
+<p>
+Even though interfaces that are not type parameters can be
+<a href="#Comparison_operators">compared</a>
+(possibly causing a run-time panic) they do not implement
+<code>comparable</code>.
+</p>
+
+<pre>
+int                          // implements comparable
+[]byte                       // does not implement comparable (slices cannot be compared)
+interface{}                  // does not implement comparable (see above)
+interface{ ~int | ~string }  // type parameter only: implements comparable
+interface{ comparable }      // type parameter only: implements comparable
+interface{ ~int | ~[]byte }  // type parameter only: does not implement comparable (not all types in the type set are comparable)
+</pre>
+
+<p>
+The <code>comparable</code> interface and interfaces that (directly or indirectly) embed
+<code>comparable</code> may only be used as type constraints. They cannot be the types of
+values or variables, or components of other, non-interface types.
+</p>
+
 <h3 id="Variable_declarations">Variable declarations</h3>
 
 <p>