package main
import (
"fmt"
"strings"
)
func main() {
/*
测试指针使用
*/
i, j := 42, 2701
p := &i
fmt.Println(*p)
*p = 21
fmt.Println(i) // 修改了i的值,说明确实指向的是地址
p = &j
*p = *p / 37
fmt.Println(j == *p) // 返回值是true,说明确实修改的是地址
/*
测试结构体的使用,打印结果:{1 2}
*/
fmt.Println(Vertex{1, 2})
//访问结构体字段
v := Vertex{4, 5}
fmt.Println(v.X * v.Y)
//结构体指针 (其实就是为了可以改变结构体里的值)
pp := &v //居然不能用上面的p来直接等于该地址
(*pp).X = 12345
pp.Y = 67890 //两种引用方式
fmt.Println(v)
//结构体的各种缺省赋值
w := Vertex{1, 0}
ww := Vertex{X: 1}
www := Vertex{}
pp = &Vertex{0, 0}
fmt.Println(w == ww, www == *pp, pp) //都是true,所以w,ww这些都是比较的值吗,确实,因为输出的都是数组似的
// 创建结构体类型的指针
ptr := &Vertex{2, 4}
ptr.X = 3
fmt.Println(ptr, ptr.X == 3, ptr.Y)
fmt.Println(v1, v2, p) //{1 2} {0 2} 0xc0000b0070 访问到TestStruct那一层的指针地址
fmt.Println(v11, v22, pp) //{1 2} {0 2} &{0 0}
/*
数组,定义了长度不可变
*/
var arr [12]int
for i := 0; i < 12; i++ {
arr[i] = i
fmt.Print(arr[i], " ")
}
primes := []int{0, 1, 2, 3, 4, 5, 6} //这里是否一定要指明长度? 这样不指明长度是切片写法,指创建了一个数组,构建了一个引用该数组的切片
fmt.Println(primes)
/*
切片:半开区间 切片不存储任何数据,只是描述了底层数组中的一段 共享改变
len代表元素的个数,cap代表容量
长度所指向数组中的元素个数
容量是指切片第一个元素到底层数组元素最后一个元素的个数
append方法,如果切片的底层数组不能容纳切片所有给定值时,切片会分配一个更大容量的数组,返回的切片会指向这个新数组
*/
var slice []int = primes[2:5] // primes[2:5]就创建了一个切片
fmt.Println(slice, len(slice), cap(slice)) //output: [2 3 4] 3 5
//slice bounds out of range
// slice = primes[99:100]
slice = primes[6:7]
fmt.Println(slice) //output: [6]
// 可以缺省上下界
slice = primes[:]
fmt.Println(slice, len(slice), cap(slice))
// 空的切片
var emptySlice []int // 这个未定义长度的就是切片。其零值是nil,其无底层数组
fmt.Println(emptySlice, len(emptySlice), cap(emptySlice)) //emptyS[0]是错误写法 ,其零值是 nil
if emptySlice == nil {
fmt.Println("nil")
}
// 空的数组
var emptyArray [0]int
fmt.Println(emptyArray)
// if emptyArray[0]==0{ 这个也不能说去访问emptyArray[0],但我不清楚在底层是否有实际数组
// fmt.Println("0")
// }
// make 创建切片 make 函数会分配一个元素为零值的数组并返回一个引用了它的切片
makeSlice := make([]int, 6) //指定长度
fmt.Println(makeSlice, len(makeSlice), cap(makeSlice))
makeSlice1 := make([]int, 2, 5) //长度为2 , 容量为 5
fmt.Println(makeSlice1, len(makeSlice1), cap(makeSlice1)) // [0 0] 2 5
makeSlice1 = makeSlice1[:cap(makeSlice1)]
fmt.Println(makeSlice1, len(makeSlice1), cap(makeSlice1))
makeSlice1 = makeSlice1[1:]
fmt.Println(makeSlice1, len(makeSlice1), cap(makeSlice1))
// 切片的切片 (二维)
board := [][]string{
[]string{"_", "_", "_"},
[]string{"_", "_", "_"},
[]string{"_", "_", "_"},
}
board[0][0] = "x"
board[0][1] = "o"
board[1][0] = "x"
board[2][0] = "o"
board[1][1] = "x"
board[2][2] = "o"
for i := 0; i < len(board); i++ {
fmt.Printf("%s\n", strings.Join(board[i], " "))
}
//Range 使用for循环遍历切片时候,每次迭代都会返回两个值,第一个值为当前元素的下标,第二个值为该下标所对应元素的一份副本
for i, j := range board {
for m, n := range j {
fmt.Println("board[", i, " ", m, "]", n)
}
}
//Range 使用时可以忽略其 下标或下标所对应元素的副本
for i := range board {
fmt.Printf("%d ", i)
}
for _, j := range board {
fmt.Println(j)
}
for i := range board {
fmt.Println(i)
}
//映射 make函数会返回给定类型的映射,并将其初始化备用
var m map[string]Vertex = make(map[string]Vertex) //make也可以用在键值对的映射里面
m["Bell Labs"] = Vertex{1, 2}
fmt.Println(m["Bell Labs"])
//多个映射
var mm = map[string]Vertex{
"Bell Labs": Vertex{1, 2},
"Google": Vertex{3, 4},
}
fmt.Println(mm)
var mmm = map[int]Vertex{
1: {1, 2},
2: {3, 4}, //可以省略掉类型
}
fmt.Println(mmm)
for _, j := range mmm {
fmt.Println(j)
}
//在映射m中插入或修改元素
ss := make(map[string]int)
ss["answer"]=42
fmt.Println("the value",ss["answer"])
ss["answer"]=48
fmt.Println("the value",ss["answer"])
delete(ss,"answer")
fmt.Println("the value",ss["answer"])
elem,ok := ss["answer"]
fmt.Println(elem,ok) // 0,false elem 没在 m中返回 false
ss["yes"]=2
elem,ok = ss["yes"]
fmt.Println(elem,ok) //2,true elme 在 m 中,所以返回其elme 值,并ok为true
// strings.Fields方法可以切分字符串
var str = make(map[string]int)
var s = "This is a test,but is not noly a test"
var c = strings.Fields(s)
for _,j := range c {
str[j] ++
}
fmt.Println(str)
}
// Vertex 是结构体
type Vertex struct {
X int
Y int
}
//TestStruct 使用结构体文法通过直接列出字段的值来分配一个结构体
type TestStruct struct {
x, y int //非导出字段,不可从包外面访问。类似不可以从该结构体外面访问?
}
//TestPipeStruct 测试导出字段的结构体(与上面相对应)
type TestPipeStruct struct {
X, Y int
}
var (
v1 = TestStruct{1, 2}
v2 = TestStruct{y: 2}
p = &TestStruct{1, 2}
)
var (
v11 = TestPipeStruct{1, 2}
v22 = TestPipeStruct{Y: 2}
pp = &TestPipeStruct{1, 2}
)