diff --git a/doc/effective_go.html b/doc/effective_go.html
index a32179298e..27bfd1bf52 100644
--- a/doc/effective_go.html
+++ b/doc/effective_go.html
@@ -59,13 +59,14 @@ prescriptive style guide.
With Go we take an unusual
approach and let the machine
take care of most formatting issues.
-A program, gofmt
, reads a Go program
+The gofmt
tool reads a Go program
and emits the source in a standard style of indentation
and vertical alignment, retaining and if necessary
reformatting comments.
If you want to know how to handle some new layout
situation, run gofmt
; if the answer doesn't
-seem right, fix the program (or file a bug), don't work around it.
+seem right, rearrange your program (or file a bug about gofmt
),
+don't work around it.
@@ -94,7 +95,7 @@ type T struct {
-All code in the libraries has been formatted with gofmt
.
+All Go code in the standard packages has been formatted with gofmt
.
container_vector
and not containerVector
.
The importer of a package will use the name to refer to its contents
(the import .
notation is intended mostly for tests and other
-unusual situations), so exported names in the package can use that fact
+unusual situations and should be avoided unless necessary),
+so exported names in the package can use that fact
to avoid stutter.
For instance, the buffered reader type in the bufio
package is called Reader
,
not BufReader
, because users see it as bufio.Reader
,
@@ -316,8 +318,8 @@ Similarly, the function to make new instances of ring.Ring
—wh
is the definition of a constructor in Go—would
normally be called NewRing
, but since
Ring
is the only type exported by the package, and since the
-package is called ring
, it's called just New
.
-Clients of the package see that as ring.New
.
+package is called ring
, it's called just New
,
+which clients of the package see as ring.New
.
Use the package structure to help you choose good names.
+Go doesn't provide automatic support for getters and setters.
+There's nothing wrong with providing getters and setters yourself,
+and it's often appropriate to do so, but it's neither idiomatic nor necessary
+to put Get
into the getter's name. If you have a field called
+owner
(lower case, unexported), the getter method should be
+called Owner
(upper case, exported), not GetOwner
.
+The use of upper-case names for export provides the hook to discriminate
+the field from the method.
+A setter function, if needed, will likely be called SetOwner
.
+Both names read well in practice:
+
+owner := obj.Owner() +if owner != user { + obj.SetOwner(user) +} ++
@@ -489,8 +512,8 @@ codeUsing(f)
-This is a example of a common situation where code must analyze a
-sequence of error possibilities. The code reads well if the
+This is an example of a common situation where code must guard against a
+sequence of error conditions. The code reads well if the
successful flow of control runs down the page, eliminating error cases
as they arise. Since error cases tend to end in return
statements, the resulting code needs no else
statements.
@@ -553,8 +576,9 @@ for _, value := range m { // key is unused
For strings, the range
does more work for you, breaking out individual
-Unicode characters by parsing the UTF-8 (erroneous encodings consume one byte and produce the
-replacement rune U+FFFD). The loop
+Unicode characters by parsing the UTF-8.
+Erroneous encodings consume one byte and produce the
+replacement rune U+FFFD. The loop
for pos, char := range "日本語" { @@ -571,8 +595,9 @@ character 語 starts at byte position 6
-Finally, since Go has no comma operator and ++
and --
-are statements not expressions, if you want to run multiple variables in a for
+Finally, Go has no comma operator and ++
and --
+are statements not expressions.
+Thus if you want to run multiple variables in a for
you should use parallel assignment.
@@ -676,7 +701,7 @@ case *int:One of Go's unusual features is that functions and methods -can return multiple values. This can be used to +can return multiple values. This form can be used to improve on a couple of clumsy idioms in C programs: in-band error returns (such as
-1
forEOF
) and modifying an argument. @@ -811,7 +836,7 @@ func Contents(filename string) (string, os.Error) {
-Deferring a function like this has two advantages. First, it
+Deferring a call to a function such as Close
has two advantages. First, it
guarantees that you will never forget to close the file, a mistake
that's easy to make if you later edit the function to add a new return
path. Second, it means that the close sits near the open,
@@ -903,8 +928,9 @@ leaving: b
For programmers accustomed to block-level resource management from
other languages, defer
may seem peculiar, but its most
interesting and powerful applications come precisely from the fact
-that it's not block-based but function based. In the section on
-panic
and recover
we'll see an example.
+that it's not block-based but function-based. In the section on
+panic
and recover
we'll see another
+example of its possibilities.
Values of type SyncedBuffer
are also ready to use immediately upon allocation
-or just declaration. In this snippet, both p
and v
will work
+or just declaration. In the next snippet, both p
and v
will work
correctly without further arrangement.
func NewFile(fd int, name string) *File { if fd < 0 { @@ -999,7 +1024,7 @@ func NewFile(fd int, name string) *File {
-Note that it's perfectly OK to return the address of a local variable;
+Note that, unlike in C, it's perfectly OK to return the address of a local variable;
the storage associated with the variable survives after the function
returns.
In fact, taking the address of a composite literal
@@ -1053,7 +1078,7 @@ is that these three types are, under the covers, references to data structures t
must be initialized before use.
A slice, for example, is a three-item descriptor
containing a pointer to the data (inside an array), the length, and the
-capacity; until those items are initialized, the slice is nil
.
+capacity, and until those items are initialized, the slice is nil
.
For slices, maps, and channels,
make
initializes the internal data structure and prepares
the value for use.
@@ -1273,7 +1298,21 @@ is not present in the map will return the zero value for the type
of the entries
in the map. For instance, if the map contains integers, looking
up a non-existent key will return 0
.
+A set can be implemented as a map with value type bool
.
+Set the map entry to true
to put the value in the set, and then
+test it by simple indexing.
+attended := map[string] bool { + "Ann": true, + "Joe": true, + ... +} + +if attended[person] { // will be false if person is not in the map + fmt.Println(person, "was at the meeting") +} +
Sometimes you need to distinguish a missing entry from
a zero value. Is there an entry for "UTC"
@@ -1298,7 +1337,7 @@ func offset(tz string) int {
if seconds, ok := timeZone[tz]; ok {
return seconds
}
- log.Println("unknown time zone", tz)
+ log.Println("unknown time zone:", tz)
return 0
}