可见性
- 声明在函数内部,是函数的本地值,类似private
- 声明在函数外部,是对当前包可见(包内所有.go文件都可见)的全局值,类似protect
- 声明在函数外部且首字母大写是所有包可见的全局值,类似public
类型
- 值类型: bool, int(32 or 64), int8, int16, int32, int64, uint(32 or 64), uint8(byte), uint16, uint32, uint64, float32, float64, string,complex64, complex128, array -- 固定长度的数组
- 引用类型:
slice -- 序列数组(最常用)
map -- 映射
chan -- 管道`
和js不同,go的array是值类型,事实上js的array特性和go的slice更加贴近,因为js的数组是变长的,而go中是定长的
展开运算符
go中展开运算符是后置的,
//展开数组或切片
a:={arr...}
//声明变参函数
func test(s string, n ...int) string {
var x int
for _, i := range n {
x += i
}
return fmt.Sprintf(s, x)
}
异常处理
go中没有try catch这样结构化的异常处理,而是使用 panic 抛出错误,recover 捕获错误。
- 程序遇到panic 后会中断后续的程序执行
-
recover的定义必须在panic 之前
,因为panic 会终止后续代码的执行,如果recover 定义在panic 后面,程序已经被中断了,所以不会生效。 - recover 必须使用defer,不然无法捕panic
- 函数G调用函数F,如果函数F抛出panic ,G也会被中断,但是G函数中的defer依旧会执行
- 连续使用defer可以连续抛出panic,但是只有最后执行的那个defer能被捕获到,也就是后抛出的panic会覆盖先抛出的panic,但是可以连续抛出捕获,例如:
func main() {
defer func() {
fmt.Println("Recovering from panic in first defer.")
if err := recover(); err != nil {
fmt.Println("Recovering from panic in second defer2:", err)
}
}()
//捕获后再次抛出
defer func() {
if err := recover(); err != nil {
fmt.Println("Recovering from panic in second defer:", err)
panic("Panic2!")
}
}()
panic("Panic!")
}
输出结果为:
image.png
panic虽然会抛出错误,但是只建议在会影响程序正常执行的时候去使用,用于中断程序的执行,其他的异常情况,建议直接返回err并且处理
网友评论