java轉go的多少踩了坑,剛開始代碼都是一堆java的思想來學習go,這個似乎是不對的,雖說語言都互有通性,但是無論是之前是學啥語言的然後來接觸go的,我想剛開始都會踩到一些坑的,當然這多數是個人的看法,也許是自身的無知,畢竟隔幾個月再去看以前的代碼也是一臉懵逼得。以下還是來看看我踩到的坑吧。
1. 理解指針
不說概念上例子:
*int 是int的指針類型;
**int是int指針的指針類型;
取變量地址用&操作符,取指針變量對應的變量的值使用*操作符
如:
func main() {
i := 0
var p *int
var pp **int
p = &i
pp = &p
*p++
// i輸出i的值
// p變量i的地址
// *p是int指針指向i的值
// pp變量p的地址
// *pp輸出的是指針p的地址
fmt.Println(i, p, *p, pp, *pp)
}
指針傳入函數的坑
func main() {
student := Student{"A", 1}
fmt.Println("set 前",student)
set(student)
fmt.Println("set 後未變",student)
fmt.Println("set 前",student)
Set(&student)
fmt.Println("set 後指針傳入值變了",student)
}
type Student struct {
Name string
Age int
}
// s中的值未變
func set(s Student) Student {
s.Age = 2
s.Name = "B"
return s
}
// 通過指針傳遞,值變了
func Set(s *Student) {
s.Age = 2
s.Name = "B"
}
2. go的訪問權限
go不像java一樣有public、private、protected這些關鍵字來修飾方法或者類等的訪問權限,它是通過首字母的大小寫來控制可見性的,go中的常量、變量、接口、函數如果首字母是大寫相當於java中的public,如
package test
import "fmt"
// 外部的文件可以訪問
func TestPointer() {
fmt.Printf("我可以訪問")
}
// 結構體Man可以外部訪問
type Man struct {
// 外部可以訪問賦值
Name string
// 不可以訪問
age int
}
3. defer關鍵字
3.1 defer的表達式必須是函數或方法的調用;
3.2 defer必須等待當前函數執行完了之後再執行,如
func testA() {
fmt.Println("testA")
}
func testB() {
fmt.Println("testB")
}
func unlock() {
fmt.Println("unlock")
}
func testDefer() {
testA()
// 在當前函數執行完之後再執行
defer unlock()
testB()
}
func main() {
testDefer()
}
想象中以爲是:testA->unlock->testB,其實輸出順序
3.3 defer所註冊的函數返回值是按照LIFO(後進先出)的次序依次執行,如:
不加defer執行結果:
func deferReturn(i int) int {
fmt.Println(i)
return i
}
func main() {
for i := 0; i < 4; i++{
deferReturn(i)
}
}
加入defer
func deferReturn(i int) int {
fmt.Println(i)
return i
}
func main() {
for i := 0; i < 4; i++{
defer deferReturn(i)
}
}
持續維護......