参考:https://www.topgoer.com/资料下载/Golang新手可能会踩的50个坑.html

1**.不能存在未使用的变量,如果有会提示错误,同时编译无法通过。**

2.不能存在未使用的 import,如果有会提示错误,同时编译无法通过。

3.简短声明的变量只能在函数内部使用.

// 错误示例
myvar := 1    // syntax error: non-declaration statement outside function body
func main() {
}

// 正确示例
var  myvar = 1
func main() {
}

4.使用简短声明来重复声明单一的变量,:=左侧至少有一个新变量,才允许多变量的重复声明

// 错误示例
func main() {  
    one := 0
    one := 1 // error: no new variables on left side of :=
}

// 正确示例
func main() {
    one := 0
    one, two := 1, 2    // two 是新变量,允许 one 的重复声明。比如 error 处理经常用同名变量 err
    one, two = two, one    // 交换两个变量值的简写
}

5.允许对值为 nil 的 slice 添加元素,但对值为 nil 的 map添加元素则会造成运行时 panic

// map 错误示例
func main() {
    var m map[string]int
    m["one"] = 1        // error: panic: assignment to entry in nil map
    // m := make(map[string]int)// map 的正确声明,分配了实际的内存
}    

// slice 正确示例
func main() {
    var s []int
    s = append(s, 1)
}

6.string 类型的变量值不能为 nil

// 错误示例
func main() {
    var s string = nil    // cannot use nil as type string in assignment
    if s == nil {    // invalid operation: s == nil (mismatched types string and nil)
        s = "default"
    }
}

// 正确示例
func main() {
    var s string    // 字符串类型的零值是空串 ""
    if s == "" {
        s = "default"
    }
}

7.在 Go 中,数组是值。作为参数传进函数时,传递的是数组的原始值拷贝,此时在函数内部是无法更新该数组的

// 数组使用值拷贝传参
func main() {
    x := [3]int{1,2,3}

    func(arr [3]int) {
        arr[0] = 7
        fmt.Println(arr)    // [7 2 3]
    }(x)
    fmt.Println(x)            // [1 2 3]    // 并不是你以为的 [7 2 3]
}

如果想修改参数数组:

// 传址会修改原数据
func main() {
    x := [3]int{1,2,3}

    func(arr *[3]int) {
        (*arr)[0] = 7
        fmt.Println(arr)    // &[7 2 3]
    }(&x)
    fmt.Println(x)    // [7 2 3]
}

// 会修改 slice 的底层 array,从而修改 slice
func main() {
    x := []int{1, 2, 3}
    func(arr []int) {
        arr[0] = 7
        fmt.Println(x)    // [7 2 3]
    }(x)
    fmt.Println(x)    // [7 2 3]
}

8.与其他编程语言中的 for-in 、foreach 遍历语句不同,Go 中的 range 在遍历时会生成 2 个值,第一个是元素索引,第二个是元素的值

// 错误示例
func main() {
    x := []string{"a", "b", "c"}
    for v := range x {
        fmt.Println(v)    // 1 2 3
    }
}

// 正确示例
func main() {
    x := []string{"a", "b", "c"}
    for _, v := range x {    // 使用 _ 丢弃索引
        fmt.Println(v)
    }
}