Go 指针, pointer

Go 指针, pointer 普通指针 uintptr unsafe.Pointer 对于Go语言, 严格意义上来讲, 只有一种传递, 也就是按值传递 (by value)。当一个变量当作参数传递的时候, 会创建一个变量的副本, 然后传递给函数或者方法, 你可以看到这个副本的地址和变量的地址是不一样的。 当变量当做指针被传递的时候, 一个新的指针被创建, 它指向变量指向的同样的内存地址, 所以你可以将这个指针看成原始变量指针的副本。当这样理解的时候, 我们就可以理解成Go总是创建一个副本按值转递, 只不过这个副本有时候是变量的副本, 有时候是变量指针的副本。 Go 语言保留着C中值和指针的区别, 但是对于指针繁琐用法进行了大量的简化,引入引用的概念。所以在Go语言中,你几乎不用担心会因为直接操作内寸而引起各式各样的错误。Go语言的指针, 基本上只剩下用于区分 by ref 和 by val 语义。 指针地址和指针类型 一个指针变量可以指向任何一个值的内存地址,它所指向的值的内存地址在 32 和 64 位机器上分别占用 4 或 8 个字节,占用字节的大小与所指向的值的大小无关。当一个指针被定义后没有分配到任何变量时,它的默认值为 nil。指针变量通常缩写为 ptr。 每个变量在运行时都拥有一个地址,这个地址代表变量在内存中的位置。Go语言中使用在变量名前面添加&操作符 (前缀)来获取变量的内存地址 (取地址操作),格式如下: ptr := &v // v 的类型为 T 其中 v 代表被取地址的变量,变量 v 的地址使用变量 ptr 进行接收,ptr 的类型为 *T,称做 T 的指针类型,* 代表指针。 // &: 取地址 // *: 解析地址 var p *int // p 的类型是: int 型的指针 // Foo, Bar 的类型是指针 type TestItem struct { Foo *string //指针类型 Bar *string } package main import "fmt" func main() { var cat int = 1 var str string = "banana" // 0xc00001a0b0 0xc000010230 fmt.Printf("%p %p", &cat, &str) } package basic import ( "fmt" ) func PointerTest() { var i int // i 的类型是 int 型 i = 1 // i 的值为 1; var p *int // p 的类型是 int型的指针 p = &i // p 的值为 i 的地址 fmt.Printf("i=%d;p=%d;*p=%d\n", i, p, *p) *p = 2 // *p 的值为 [[i的地址]的指针] (其实就是i), 这行代码也就等价于 i = 2 fmt.Printf("i=%d;p=%d;*p=%d\n", i, p, *p) i = 3 // 验证想法 fmt.Printf("i=%d;p=%d;*p=%d\n", i, p, *p) } 这段代码执行结果: ...

2016-10-12 · 7 min · 1431 words · -