# 分組聲明
~~~
import "fmt"
import "os"
const i = 100
const ii = 3.1415
const iii = "test"
var i int
var ii float64
var iii string
//分組代碼如下
import(
"fmt"
"os"
)
const(
i = 1
ii = 3.1415
iii = "test"
)
var (
i int
ii float64
iii string
)
~~~
# iota枚舉
這個關鍵字用來聲明enum的時候用,它默認開始值是0,每調用一次+1.
~~~
package main
import "fmt"
const (
x = iota
y = iota
z = iota
w
)
const v = iota //每遇到const關鍵字,iota就會重置
func main() {
fmt.Printf("x=%d\ny=%d\nz=%d\nw=%d\nv=%d", x, y, z, w, v)
}
~~~

**大寫字母開頭的變量是可導出的,即其他包可以讀取,是公用變量**
**小寫字母開頭的不可導出,是私有變量**
**大寫字母開頭的函數也一樣,相當于class中帶public關鍵字詞的公有函數**
**小寫字母開頭的函數,就是有private關鍵詞的私有函數**
# array數組
在[n]array中,
n表示數組的長度
type表示存儲元素的類型
~~~
var arr [n]array
~~~
~~~
package main
import "fmt"
func main() {
var arr [5]int //聲明了一個int類型的數值
arr[0] = 10
arr[4] = 20
fmt.Printf("This first is %d\n", arr[0])
fmt.Printf("This last is %d\n", arr[4])
}
~~~

說明:長度也是數組類型的一部分,因此[5]int與[10]int是不同的類型,數組也就不能改變長度。
如果使用指針,就需要用到slice類型
~~~
package main
import "fmt"
func main() {
a := [5]int{1,2,3,4,5} //聲明了一個長度為5的int數組
b := [...]int{7,8,9} //可以省略長度,`...`的方式,會自動根據元素個數來計算長度
c := [2][4]int{1,2,3,4},{5,6,7,9} //聲明了一個二維數組,兩個數組作為元素,每個數組中又有4個int類型的元素
}
~~~
# slice
在初始定義數組時,我們并不知道需要多大的數組,因此我們就需要“動態數組”,這種數據結構叫slice。
slice并不是真正意義上的動態數組,而是一個引用類型。
slice總是指向一個底層array
~~~
//聲明和array一樣,只是少了長度
var a []int
~~~
slice通過 array[i:j]來獲取,其中i是數組的開始位置,j是結束為止,但不包含array[j],
~~~
//聲明一個含有5個元素類型為byte的數組
test := [5]byte{'a', 'b', 'c', 'd', 'e'}
//聲明兩個含有byte的slice
var a, b []byte
a = test[1:3] //test[1],test[2]
b = test[3:5] //test[3],test[4]
~~~
1、slice的默認開始位置0,test[:n]等價于test[0:n]
2、slice的第二個序列默認是數組的長度,test[n:] 等價于 test[n:len[test]]
3、如果直接獲取slice,可以使用test[:]
# map
map讀取和設置也類似slice一樣,通過key來操作,只是slice的index只能是int類型,而map多了很多類型,可以是int,string及所有完全定義了 == 與 != 操作的類型。
~~~
package main
import "fmt"
func main() {
//聲明一個key是字符串,值為int的字典,這種聲明需要在使用之前使用make初始化
//var numbers map[string]int
//另一種map的聲明方式
numbers := make(map[string]int)
numbers["test"] = 1
numbers["test1"] = 2
numbers["test2"] = 3
fmt.Println("test2:", numbers["test2"])
}
~~~
### map的初始化
可以通過key:val的方式初始化值,同時map內置有判斷是否存在key的方式
~~~
package main
import "fmt"
func main() {
//初始化一個字典
test := map[string]float32{"a": 1, "b": 2, "c": 3}
//map有兩個返回值,第二個返回值,如果不存在key返回flase,如果存在key返回true
testArr, result := test["a"]
if result {
fmt.Println("value:", testArr)
} else {
fmt.Println("key不存在")
}
}
~~~
### 通過delete刪除map元素
~~~
delete(testArr,"a") //刪除key為a的元素
~~~
### map是一種引用類型
如果兩個map同時指向一個底層,那么一個改變,另一個也相應改變
~~~
package main
import "fmt"
func main() {
m := make(map[string]string)
m["test"] = "test"
m1 := m
m1["test"] = "change test" //現在,m["test"]的值也已經是chage test了
fmt.Printf("改變后的test:%s", m["test"])
}
~~~

# make,new操作
### make
make用于內建類型(map、slice、channel)的內存分配
make(T,args)與new(T)有著不同的功能,make只能創建slice,map,channel,并且返回一個有初始值(非零)的T類型,而不是*T
### new
new用于各種類型的內存分配【new返回指針】
new(T)分配了零值填充的T類型的內存空間,并且返回其地址,即一個*T類型的值(GO語言的術語:返回了一個指針,指向新分配的類型T的零值)
**總結:**
new 負責分配內存,new(T) 返回*T 指向一個零值 T 的指針
make 負責初始化值,make(T) 返回初始化后的 T ,而非指針
最重要的一點:make 僅適用于slice,map 和channel
關于“零值”,并非是空值,而是一種“變量未填充前”的默認值,通常為0,如下
~~~
int 0
int8 0
int32 0
int64 0
uint 0x0
rune 0 //rune的實際類型是 int32
byte 0x0 //byte的實際類型是uint8
float32 0 //長度為4 byte
float64 0 //長度為8 byte
bool false
string ""
~~~
- 前言
- golang學習(一)之安裝
- Go語言學習二:Go基礎(變量、常量、數值類型、字符串、錯誤類型)
- Go語言學習三:Go基礎(iota,array,slice,map,make,new)
- Go語言學習四:struct類型
- Ubuntu 14.04/CentOS 6.5中安裝GO LANG(GO語言)
- Mac OS 安裝golang
- Mac install Thrift
- Thrift RPC 使用指南實戰(附golang&PHP代碼)
- golang net/http包使用
- 冒泡排序Bubble sort-golang
- 快速排序Quick sort - golang
- Go語言學習:Channel是什么?
- Golang的select/非緩沖的Channel實例詳解
- Golang time包的定時器/斷續器
- Golang同步:鎖的使用案例詳解
- Golang同步:條件變量和鎖組合使用
- Golang同步:原子操作使用
- Golang之bytes.buffer
- Golang之字符串格式化
- Golang之反射reflect包
- Go語言配置文件解析器,類似于Windows下的INI文件.