Index out of bounds are not checked at compile time for slices (including strings, a.k.a. slices of bytes).
You may consider using the indexing functions from the gosugar package instead, which will automatically check slice length for you.
nil
The compiler does not check nullability for functions, interfaces, and pointers.
Thus any function taking a function, an interface, or a pointer,
need to check whether input is nil
itself.
Since all methods implicitly accepts a pointer,
all methods should check whether its receiver is nil
or not.
Though, if you are careful enough, you may omit checking nullability in unexported functions.
You can use the RequireNonNull function from goaround package
to check every not nullable parameters,
which will panic if the parameter passed in is nil
.
Use the var _ Interface = (*Type)(nil)
trick.
if
to declare variablesLike for
, the if
statement can start with a short statement to execute before the condition.
This often harms readability thus it should only be used to declare variables to limit their scope.
Same applies to switch
.
In Go, switch
can be used for both case
and cond
.
To avoid confusion, I always use switch
for case
.
I use if ... else if
instead of switch
for cond
.
Use defer
carefully.
Do not rely on Go’s default initialized value. Initialize it explicitly instead if the value is intended to be used later.
The program should be semantically equivalent if Go changed zero values of default initialization.
Similarly, always check presentence when retrieving elements from a map.
For example, if you want to retrieve an integer from a map,
and use 0
if the key is missing:
element := m["id"]
The above code utilizes the zero value of missing keys. This makes the code shorter, but less clear (The value is absent? The value happens to be zero?)
Verbose and explicit code is preferred:
element, present := m["id"]
if present {
return element
} else {
return 0
}
Since Go will always initialize zero value on declaration, the compiler will not complain declaration without initialization. Thus we should initialize variable on declaration whenever possible. For example, the following code:
var s string
if x < 0 {
s = "0"
} else {
s = "1"
}
can be extracted as a function:
func f(x int) {
if x < 0 {
return "0"
} else {
return "1"
}
}
var s string = f(5)
since the compiler will check the function returns on all branches.
%#q
in printf
There are more good things to remember than the special rules of %#q
.