下面是摘抄出来的几个:
SA6001 – Missing an optimization opportunity when indexing maps by byte slices
Map keys must be comparable, which precludes the use of byte slices. This usually leads to using string keys and converting byte slices to strings.
Normally, a conversion of a byte slice to a string needs to copy the data and causes allocations. The compiler, however, recognizes m[string(b)]
and uses the data of b
directly, without copying it, because it knows that the data can’t change during the map lookup. This leads to the counter-intuitive situation that
k := string(b)
println(m[k])
println(m[k])
will be less efficient than
println(m[string(b)])
println(m[string(b)])
because the first version needs to copy and allocate, while the second one does not.
For some history on this optimization, check out commit f5f5a8b6209f84961687d993b93ea0d397f5d5bf in the Go repository.
Available since
2017.1
SA6005 – Inefficient string comparison with strings.ToLower
or strings.ToUpper
Converting two strings to the same case and comparing them like so
if strings.ToLower(s1) == strings.ToLower(s2) {
…
}
is significantly more expensive than comparing them with strings.EqualFold(s1, s2)
. This is due to memory usage as well as computational complexity.
strings.ToLower
will have to allocate memory for the new strings, as well as convert both strings fully, even if they differ on the very first byte. strings.EqualFold, on the other hand, compares the strings one character at a time. It doesn’t need to create two intermediate strings and can return as soon as the first non-matching character has been found.
For a more in-depth explanation of this issue, see https://blog.digitalocean.com/how-to-efficiently-compare-strings-in-go/
Available since
2019.2
SA9003 – Empty body in an if or else branc