diff options
author | Rob Pike <r@golang.org> | 2010-11-01 21:46:04 -0700 |
---|---|---|
committer | Rob Pike <r@golang.org> | 2010-11-01 21:46:04 -0700 |
commit | 0808b199e0f6c3143c706a3a489dc727868b19fc (patch) | |
tree | fbe4d6278472a2bd6e01d87fcea7e2852a7ecab7 | |
parent | c33289238e8e48f8163a3a9f44979975ad068a6b (diff) | |
download | go-0808b199e0f6c3143c706a3a489dc727868b19fc.tar.gz go-0808b199e0f6c3143c706a3a489dc727868b19fc.zip |
Effective Go: append and a few words about ...
R=rsc, gri, iant
CC=golang-dev
https://golang.org/cl/2821041
-rw-r--r-- | doc/effective_go.html | 50 |
1 files changed, 50 insertions, 0 deletions
diff --git a/doc/effective_go.html b/doc/effective_go.html index 3e1b64dbf6..075f863195 100644 --- a/doc/effective_go.html +++ b/doc/effective_go.html @@ -1218,6 +1218,11 @@ func Append(slice, data[]byte) []byte { We must return the slice afterwards because, although <code>Append</code> can modify the elements of <code>slice</code>, the slice itself (the run-time data structure holding the pointer, length, and capacity) is passed by value. +<p> +The idea of appending to a slice is so useful it's captured by the +<code>append</code> built-in function. To understand that function's +design, though, we need a little more information, so we'll return +to it later. </p> @@ -1465,6 +1470,10 @@ func Println(v ...interface{}) { } </pre> <p> +We write <code>...</code> after <code>v</code> in the call to <code>Output</code> to tell the +compiler to treat <code>v</code> as a list of arguments; otherwise it would just pass +<code>v</code> as a single slice argument. +<p> There's even more to printing than we've covered here. See the <code>godoc</code> documentation for package <code>fmt</code> for the details. </p> @@ -1484,6 +1493,47 @@ func Min(a ...int) int { } </pre> +<h3 id="append">Append</h3> +<p> +Now we have the missing piece we needed to explain the design of +the <code>append</code> built-in function. The signature of <code>append</code> +is different from our custom <code>Append</code> function above. +Schematically, it's like this: +<pre> +func append(slice []<i>T</i>, elements...T) []<i>T</i> +</pre> +where <i>T</i> is a placeholder for any given type. You can't +actually write a function in Go where the type <code>T</code> +is determined by the caller. +That's why <code>append</code> is built in: it needs support from the +compiler. +<p> +What <code>append</code> does is append the elements to the end of +the slice and return the result. The result needs to be returned +because, as with our hand-written <code>Append</code>, the underlying +array may change. This simple example +<pre> +x := []int{1,2,3} +x = append(x, 4, 5, 6) +fmt.Println(x) +</pre> +prints <code>[1 2 3 4 5 6]</code>. So <code>append</code> works a +little like <code>Printf</code>, collecting an arbitrary number of +arguments. +<p> +But what if we wanted to do what our <code>Append</code> does and +append a slice to a slice? Easy: use <code>...</code> at the call +site, just as we did in the call to <code>Output</code> above. This +snippet produces identical output to the one above. +<pre> +x := []int{1,2,3} +y := []int{4,5,6} +x = append(x, y...) +fmt.Println(x) +</pre> +Without that <code>...</code>, it wouldn't compile because the types +would be wrong; <code>y</code> is not of type <code>int</code>. + <h2 id="initialization">Initialization</h2> <p> |