From 0d8aa8cce69f97747e7ce69b8416c1cfca5d939f Mon Sep 17 00:00:00 2001 From: Robert Griesemer Date: Thu, 12 Dec 2024 15:26:54 -0800 Subject: [PATCH] spec: describe representation of values Add a section on the representation of values: distinguish between values that are self-contained and values that contain references while avoiding the notion of "reference types" which is misleading. Also, use "predeclared identifier nil" rather than "predeclared value nil" because it is the identifier that is predeclared. Fixes #5083. Change-Id: I2235673c6404f2c055f195e879f198c7ab246d58 Reviewed-on: https://go-review.googlesource.com/c/go/+/635801 Reviewed-by: Rob Pike Reviewed-by: David Chase Auto-Submit: Robert Griesemer Reviewed-by: Ian Lance Taylor TryBot-Bypass: Robert Griesemer Reviewed-by: Robert Griesemer --- doc/go_spec.html | 91 ++++++++++++++++++++++++++++++++++++++++++------ 1 file changed, 81 insertions(+), 10 deletions(-) diff --git a/doc/go_spec.html b/doc/go_spec.html index fff489c33a..8ff178e281 100644 --- a/doc/go_spec.html +++ b/doc/go_spec.html @@ -1,6 +1,6 @@ @@ -798,7 +798,6 @@ If a variable has not yet been assigned a value, its value is the zero value for its type.

-

Types

@@ -1200,7 +1199,7 @@ type (

A pointer type denotes the set of all pointers to variables of a given type, called the base type of the pointer. -The value of an uninitialized pointer is nil. +The value of an uninitialized pointer is nil.

@@ -1216,9 +1215,9 @@ BaseType    = Type .
 

Function types

-A function type denotes the set of all functions with the same parameter -and result types. The value of an uninitialized variable of function type -is nil. +A function type denotes the set of all functions with the same parameter and result types. +The value of an uninitialized variable of function +type is nil.

@@ -1267,7 +1266,8 @@ An interface type defines a type set.
 A variable of interface type can store a value of any type that is in the type
 set of the interface. Such a type is said to
 implement the interface.
-The value of an uninitialized variable of interface type is nil.
+The value of an uninitialized variable of
+interface type is nil.
 

@@ -1630,7 +1630,7 @@ implements the interface.
 A map is an unordered group of elements of one type, called the
 element type, indexed by a set of unique keys of another type,
 called the key type.
-The value of an uninitialized map is nil.
+The value of an uninitialized map is nil.
 

@@ -1693,7 +1693,7 @@ to communicate by
 sending and
 receiving
 values of a specified element type.
-The value of an uninitialized channel is nil.
+The value of an uninitialized channel is nil.
 

@@ -1772,6 +1772,57 @@ received in the order sent.
 
 

Properties of types and values

+

Representation of values

+ +

+Values of predeclared types (see below for the interfaces any +and error), arrays, and structs are self-contained: +Each such value contains a complete copy of all its data, +and variables of such types store the entire value. +For instance, an array variable provides the storage (the variables) +for all elements of the array. +The respective zero values are specific to the +value's types; they are never nil. +

+ +

+Non-nil pointer, function, slice, map, and channel values contain references +to underlying data which may be shared by multiple values: +

+ +
    +
  • + A pointer value is a reference to the variable holding + the pointer base type value. +
  • +
  • + A function value contains references to the (possibly + anonymous) function + and enclosed variables. +
  • +
  • + A slice value contains the slice length, capacity, and + a reference to its underlying array. +
  • +
  • + A map or channel value is a reference to the implementation-specific + data structure of the map or channel. +
  • +
+ +

+An interface value may be self-contained or contain references to underlying data +depending on the interface's dynamic type. +The predeclared identifier nil is the zero value for types whose values +can contain references. +

+ +

+When multiple values share underlying data, changing one value may change another. +For instance, changing an element of a slice will change +that element in the underlying array for all slices that share the array. +

+

Underlying types

@@ -2899,7 +2950,7 @@ initialization value in the assignment. If that value is an untyped constant, it is first implicitly converted to its default type; if it is an untyped boolean value, it is first implicitly converted to type bool. -The predeclared value nil cannot be used to initialize a variable +The predeclared identifier nil cannot be used to initialize a variable with no explicit type.

@@ -6263,6 +6314,26 @@ to the type of the operand to which it is assigned, with the following special c +

+When a value is assigned to a variable, only the data that is stored in the variable +is replaced. If the value contains a reference, +the assignment copies the reference but does not make a copy of the referenced data +(such as the underlying array of a slice). +

+ +
+var s1 = []int{1, 2, 3}
+var s2 = s1                    // s2 stores the slice descriptor of s1
+s1 = s1[:1]                    // s1's length is 1 but it still shares its underlying array with s2
+s2[0] = 42                     // setting s2[0] changes s1[0] as well
+fmt.Println(s1, s2)            // prints [42] [42 2 3]
+
+var m1 = make(map[string]int)
+var m2 = m1                    // m2 stores the map descriptor of m1
+m1["foo"] = 42                 // setting m1["foo"] changes m2["foo"] as well
+fmt.Println(m2["foo"])         // prints 42
+
+

If statements

-- 2.48.1