Go中的指针
学Java以来,让程序员忽略了指针和内存地址这些概念,Java帮我们封装了对象,简化了对象引用之间的关系。在Go语言中,又帮我们回忆起这些概念。
我们创建的每一个对象在内存中都有一个位置去存储,每个内存块都有一个地址表示当前位置,通常用十六进制表示,如0x24005676543。Go语言取地址的符号是&。放在一个变量前使用就会返回相应变量的内存地址。
比如下面的代码:
var a = 3
fmt.Printf("num is : %d, it's location in memory: %p\n", a, &a)
输出:
num is : 3, it's location in memory: 0xc000062080
可以看到&a输出了a的内存地址。
你可以将&a赋值给一个变量,然后观察这个变量的类型,使用reflect.TypeOf()
方法:
var a = 3
intP = &a
b := &a
fmt.Println(reflect.TypeOf(b))
输出:
*int
可以看到&a的返回类型是 *int。
我们可以将一个变量的内存地址放在一个叫做指针的特殊数据类型中,声明一个指针的方式如下:
var p *int
然后我们可以使用p去指向一个内存地址:
p = &a
那么我们如何通过指针来获取对应内存地址的值呢,这也是有办法的。你可以在指针类型前面加上 * 号(前缀)来获取指针所指向的内容,这里的 * 号是一个类型更改器。使用一个指针引用一个值被称为间接引用。
var p *int
var a = 3
p = &a
fmt.Println(*p)
*p打印的是a的值。
当一个指针被定义没有分配任何变量的时候,它的值为nil。
对于任何一个变量val,如下表达式都是正确的:
var == *(&var)
有如下你需要注意的是,你不能获取到一个常量或者一个没有赋值操作的文字的内存地址:
const PI = 3.14
piP := &PI Cannot take the address of 'PI'
p2 := &3 Cannot take the address of '3'
在c语言中,指针是可以由程序员自行控制移动位置的,这无疑给程序增加了很多的不确定性,在Go中指针的概念其实更相当于是Java中的引用。它比Java中的引用高级之处在于:
Java中的参数传递,传递的是值的拷贝,但是在Go中你可以使用指针来传递这个值,它直接指向了这个值的内存地址,并且只占用了4个或者8个字节。
Go 默认使用按值传递来传递参数,也就是传递参数的副本。函数接收参数副本之后,在使用变量的过程中可能对副本的值进行更改,但不会影响到原来的变量 。如果你希望函数可以直接修改参数的值,而不是对参数的副本进行操作,你需要将参数的地址(变量名前面添加&符号,比如 &variable)传递给函数,这就是按引用传递 。此时传递给函数的是一个指针 。
最新文章
- 萌新笔记——Cardinality Estimation算法学习(一)(了解基数计算的基本概念及回顾求字符串中不重复元素的个数的问题)
- 艺萌TCP文件传输及自动更新系统介绍(TCP文件传输)(四)
- GDB 调试遇到??的问题
- linux文件操作命令--转
- Linux 启动直接进入 console,
- HTTP协议(4)
- (转)C++设计模式——观察者模式
- Cantor表(中等)
- LeetCode OJ 41. First Missing Positive
- 标准会话对象——StandardSession
- Mybatis 批量添加,批量更新
- python监控机器(第1版)
- debian 9 开机启动
- [Ynoi2018]未来日记
- Javascript - ExtJs - 整合百度文章编辑器
- java se的那些细节
- vue里面引入jq的方法
- system.data.sqlite的源代码下载
- Java(Android)线程池[转]
- TCP协议的特点
热门文章
- HDU 6207:Apple(Java高精度)
- scrapy基础知识之 CrawlSpiders(爬取腾讯校内招聘):
- 机器学习经典算法之PageRank
- 【深入浅出-JVM】(6):栈帧.
- 关于在记事本写入";\n";不显示换行的原因
- Oracle修改字段类型报错:“ORA-01439:要更改数据类型,则要修改的列必须为空”
- html提示框插件
- bootstrap table 父子表实现【无限级】菜单管理功能
- c的格式输出“%”
- Spring applicationContext爆出警告“Resource leak: 'applicationContext' is never closed”