1. 程式人生 > 實用技巧 >Go語言的學習之旅【五】

Go語言的學習之旅【五】

一、切片Slice

func main() {
	fmt.Println("Hello, World!")
	s := []int{1, 2, 3} //陣列
	printSlice(s)
	fmt.Println(s[0:2]) //使用切片方式
	fmt.Println(s[:2])
	fmt.Println(s[0:])
	fmt.Println(s[:])
	s2 := make([]int, 3, 5) //通過make([]int, len, cap)來定義切片
	printSlice(s2)
	var s3 []int
	if s3 == nil {
		fmt.Println("s3切片為空")
	}
	printSlice(s3)
	var s4 []int
	s4 = append(s4, 0) //向s4空切片追加資料
	printSlice(s4)
	s4 = append(s4, 1) //向s4追加1個數據
	printSlice(s4)
	s4 = append(s4, 2,3,4) //向s4追加多個數據
	printSlice(s4)
	s5 := make([]int, len(s4), cap(s4) * 2) //建立s5切片,容量是其兩倍
	printSlice(s5)
	copy(s5, s4) //將s4的內容拷貝到s5中
	printSlice(s5)
	s5 = append(s5, 6,7,8,9,10,11,12,13)//當新增的資料大於容量,會自動擴容
	printSlice(s5)
	//s5[13] = 14 //使用下標的情況,需要小於長度
	s5 = append(s5, 14,15,16,17,18,19,20,21,22,23,24,25) 
	printSlice(s5)//可以看到cap容量擴容都是兩倍擴容


}
func printSlice(x []int){
	//切片不僅能使用len()來進行測量長度,還提供了cap()函式測量容量
	fmt.Printf("len=%d cap=%d slice=%v\n",len(x),cap(x),x)
}

  

二、範圍Range

func main() {
	fmt.Println("Hello, World!")
	arr := []int{1, 2, 3}
	for num := range arr { //如果定義一個變數來接收,是其下標值
		fmt.Println(num)
	}
	for i, num := range arr { //i是下標,num是值,可以看出key,value兩個返回值
		fmt.Println(i, "", num)
	}
	for _, num := range arr { //如果不需要其中的某個返回值,直接用`_`來代替
		fmt.Println(num)
	}
	m := map[string]string{"a": "apple", "b": "banana"}
	for k, v := range m {//迴圈雜湊表
		fmt.Println(k,v)
	}
	s := "golang"
	for i,c := range s{ //迴圈字串,第一個引數是字元的索引,第二個是字元(Unicode的值)本身。
		fmt.Println(i,c)
	}
}

 

三、集合Map

func main() {
	fmt.Println("Hello, World!")
	var m map[string]string       //宣告map, map[key型別]value型別
	m2 := make(map[string]string) //用make宣告map
	if m == nil {                 //空map
		fmt.Println(m)
	}
	m2["abc"] = "ABC"      //存入值
	fmt.Println(m2["abc"]) //取出值
	m2["啊"] = "啊啊啊"
	for k, v := range m2 { //迴圈取值
		fmt.Println(k, v, m2[k])
	}
	val, ok := m2["abc"] //兩個返回值,第一個是值,第二個是狀態
	fmt.Println("val,ok:", val, ok)
	fmt.Println(m2)
	delete(m2, "abc")//刪除 key為abc
	fmt.Println(m2)
	//連結串列
	type LinkMap struct {
		key string
		value string
		next *LinkMap
	}
	alink := LinkMap{"a","A",nil}
	blink := LinkMap{"b","B",nil}
	alink.next = &blink //只能儲存其地址
	fmt.Println(alink,alink.next)
}

 

四、遞迴

func Factorial(n uint32) (res uint32) {//來個階乘n!,遞迴
	if n > 0 {
		return n * Factorial(n-1)
	}
	return 1
}
func main() {
	res := Factorial(10) 
	fmt.Println(res)
}

func Fibonacci(n int) int {//斐波那契數列
	if n < 2 {
		return n
	}
	return Fibonacci(n-1) + Fibonacci(n-2)
}
func main() {
	var i int
	for i = 0; i < 10; i++ {
		res := Fibonacci(i)
		fmt.Println(res)
	}
}

 

五、型別轉換

func main() {
   var a int32 = 10
   var b int64 = 3
   //b = a //不支援隱式轉換,報錯Cannot use 'a' (type int32) as type int64
   //b = int64(a) //顯式轉換就可以了
   var c float32
   c = float32(a) / float32(b)     //需要轉換
   var d = float32(a) / float32(b) //這個時候d可以不需要宣告型別
   var e = c + float32(b) 
   fmt.Println(c, d)
}

  

六、總結

  切片(slice)、範圍(range)、集合Map、遞迴函式基本上跟其他大部分語言都差不多。切片沒有步長(類似python的array[::-1]就倒序),集合Map返回兩個值,一個狀態值。型別轉換必須顯式.