专栏首页golang小白成长记golang面试题:能说说uintptr和unsafe.Pointer的区别吗?

golang面试题:能说说uintptr和unsafe.Pointer的区别吗?

问题

能说说uintptr和unsafe.Pointer的区别吗?

怎么答

  • unsafe.Pointer只是单纯的通用指针类型,用于转换不同类型指针,它不可以参与指针运算;
  • 而uintptr是用于指针运算的,GC 不把 uintptr 当指针,也就是说 uintptr 无法持有对象, uintptr 类型的目标会被回收;
  • unsafe.Pointer 可以和 普通指针 进行相互转换;
  • unsafe.Pointer 可以和 uintptr 进行相互转换。

举例

  • 通过一个例子加深理解,接下来尝试用指针的方式给结构体赋值。
package main

import (
 "fmt"
 "unsafe"
)

type W struct {
 b int32
 c int64
}

func main() {
 var w *W = new(W)
 //这时w的变量打印出来都是默认值0,0
 fmt.Println(w.b,w.c)

 //现在我们通过指针运算给b变量赋值为10
 b := unsafe.Pointer(uintptr(unsafe.Pointer(w)) + unsafe.Offsetof(w.b))
 *((*int)(b)) = 10
 //此时结果就变成了10,0
 fmt.Println(w.b,w.c)
}
  • uintptr(unsafe.Pointer(w)) 获取了 w 的指针起始值
  • unsafe.Offsetof(w.b) 获取 b 变量的偏移量
  • 两个相加就得到了 b地址值,将通用指针 Pointer 转换成具体指针 ((*int)(b)),通过 * 符号取值,然后赋值。*((*int)(b)) 相当于把 (*int)(b) 转换成 int 了,最后对变量重新赋值成 10,这样指针运算就完成了。
如果喜欢我的文章,可关注我的公众号:golang小白成长记

本文分享自微信公众号 - golang小白成长记(golangxbczj),作者:胖虎

原文出处及转载信息见文内详细说明,如有侵权,请联系 yunjia_community@tencent.com 删除。

原始发表时间:2020-06-02

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

我来说两句

0 条评论
登录 后参与评论

相关文章

  • Go语言学习之cgo(golang与C语言相互调用)

    几乎所有的编程语言都有C语言的影子,当然golang也不例外。可以看到golang的创始者们与c language有着密切的联系。所有,golang和c语言的相...

    李海彬
  • Golang 语言中的非类型安全指针

    Golang 语言中的 unsafe 包中包含的操作会绕过 Golang 程序的类型安全检查,直接操作内存,从而达到提升性能的目的。导入 unsafe 包可能是...

    frank.
  • Go里面的unsafe包详解

    原文:http://www.tapirgames.com/blog/golang-unsafe

    我的小碗汤
  • Golang下通过syscall调用win32的api

    源于golang群中再次提到windows下获取磁盘空间的方法 由于golang的api并非完全跨平台, golang本身并没有直接提供windows下的方式 ...

    李海彬
  • 提高 golang 的反射性能

    golang 的反射很慢。这个和它的 api 设计有关。在 java 里面,我们一般使用反射都是这样来弄的。 ---- Field field = clazz....

    李海彬
  • 深度解密Go语言之unsafe

    个人认为,学习本身并不是一件轻松愉快的事情,寓教于乐是个美好的愿望。想要深刻地领悟,就得付出别人看不见的努力。学习从来都不会是一件轻松的事情,枯燥是正常的。耐住...

    梦醒人间
  • 【Go】深入剖析slice和array

    array 和 slice 看似相似,却有着极大的不同,但他们之间还有着千次万缕的联系 slice 是引用类型、是 array 的引用,相当于动态数组, 这些都...

    thinkeridea
  • 小玩意:golang加载执行shellcode

    今天看到一个比较好玩的东西,虽然原理很简单,但是使用golang来做还是挺新鲜,所以还是分享给大家。

    七夜安全博客
  • Golang又一个和RLock有关的小故事

    前几天看了一篇golang的文章一个和RLock有关的小故事, 发现作者得到的结论是错误的, 实际涉及内容比作者讲解的多一些。

    乔碧萝殿下
  • Golang反射机制的实现分析——reflect.Type方法查找和调用

            在《Golang反射机制的实现分析——reflect.Type类型名称》一文中,我们分析了Golang获取类型基本信息的流程。本文将基于上述知识...

    方亮
  • Golang 语言怎么高效使用字符串?

    在 Golang 语言中,string 类型的值是只读的,不可以被修改。如果需要修改,通常的做法是对原字符串进行截取和拼接操作,从而生成一个新字符串,但是会涉及...

    frank.
  • 你不知道的Go unsafe.Pointer uintptr原理和玩法

    这个类型比较重要,它是实现定位和读写的内存的基础,Go runtime大量使用它。官方文档对该类型有四个重要描述:

    sunsky
  • 【转】Go Interface 源码剖析

    源网址:http://legendtkl.com/2017/07/01/golang-interface-implement/

    lpxxn
  • Golang升级到1.7后,之前正确的函数出现错误,分析原因及解决办法

    最近尝试把开发环境,升级到Golang1.7.1后,程序会偶发性的宕掉,查看日志后,发现总是在一个计算切片的哈希值的地方,错误信息是:

    henrylee2cn
  • Golang反射机制的实现分析——reflect.Type类型名称

            现在越来越多的java、php或者python程序员转向了Golang。其中一个比较重要的原因是,它和C/C++一样,可以编译成机器码运行,这保...

    方亮
  • 深入理解 Go map:赋值和扩容迁移

    在 上一章节 中,数据结构小节里讲解了大量基础字段,可能你会疑惑需要 #&(!……#(!¥! 来干嘛?接下来我们一起简单了解一下基础概念。再开始研讨今天文章的重...

    李海彬
  • 深度解密Go语言之map

    这篇文章主要讲 map 的赋值、删除、查询、扩容的具体执行过程,仍然是从底层的角度展开。结合源码,看完本文一定会彻底明白 map 底层原理。

    梦醒人间
  • 深度解密Go语言之map

    这篇文章主要讲 map 的赋值、删除、查询、扩容的具体执行过程,仍然是从底层的角度展开。结合源码,看完本文一定会彻底明白 map 底层原理。

    李海彬
  • 再谈谈获取 goroutine id 的方法

    去年年初的时候曾经写过一篇关于如何获取goroutine id的方法: 如何得到goroutine 的 id?, 当时调研了一些一些获取goid的方法。基本的方...

    李海彬

扫码关注云+社区

领取腾讯云代金券