首页 > 其他分享 >Go面试题——逃逸分析

Go面试题——逃逸分析

时间:2023-04-11 16:33:06浏览次数:37  
标签:面试题 变量 编译器 逃逸 内存 Go 分配

Go面试题——逃逸分析

  一个变量是在堆分配,还是在栈上分配,是经过编译器的逃逸分析之后得出的 "结论"。

一、逃逸分析是什么?

  在 C 语言中,可以使用mallocfree手动在堆上分配和回收内存。

  在 Go 语言中,堆内存是通过垃圾回收机制自动管理的,无需开发者指定。那么,Go 编译器怎么知道某个变量需要分配在栈上,还是堆上呢?编译器决定内存分配位置的方式,就称之为逃逸分析(escape analysis)。逃逸分析由编译器完成,作用于编译阶段。

二、逃逸分析有什么作用?

  在 Go 语言中,逃逸分析把变量合理地分配到它该去的地方,“找准自己的位置”。即使是用 new 函数申请到的内存,   如果编译器发现这块内存退出函数后就没有使用了,那就分配到栈上,毕竟栈上的内存分配比堆快很多。   即使表面上只有一个普通的变量,但是经过编译器的逃逸分析后发现,在函数之外,还有其他的地方在引用,那就分配到堆上。   如果变量都分配到堆上,堆不像栈可以自动清理。就会引起 Go 频繁地进行垃圾回收,而垃圾回收会占用比较大的系统开销。   堆和栈相比,堆适合不可预知大小的内存分配。但是为此付出的代价是分配速度较慢,而且会形成内存碎片;栈内存分配则会非常的快,栈分配内存值需要通过 PUSH 指令,并且会被自动释放;而堆内存首先需要找到一个大小合适的内存块,之后需要通过垃圾回收才能释放。   通过逃逸分析,可以尽量把哪些不需要分配到堆上的变量直接分配到栈上,堆上的变量少了,会减轻堆内存分配的开销,同时会减少垃圾回收(Garbage Collection,GC)的压力,提高程序的运行速度。

三、逃逸分析是怎么完成的?

  在 Go 语言中,逃逸分析最基本的原则是:如果一个函数返回对一个变量的引用,那么这个变量就会发生逃逸。

  编译器会分析代码的特征和代码的生命周期 ,Go 中的变量只有在编译器可以证明在函数返回后不会再被引用的,才分配到栈上,其他情况下都是分配的堆上。

  例如:对于一个变量取地址,可能会被分配到堆上。但是编译器进行逃逸分析后,如果考虑到在函数返回后,此变量不会被用,那么还是会分配到栈上。简单地来说,编译器会根据变量是否被外部引用来决定是否逃逸:

1)如果变量在函数外部没有引用,则优先放到栈上。

2)针对第一条,定义一个很大的数组,需要申请内存过大,超过栈的存储能力,一般还是要放在堆上面。

3)如果变量在函数外部存在引用,则必定放到堆上。

 四、如何确定是否发生逃逸?

 

 

标签:面试题,变量,编译器,逃逸,内存,Go,分配
From: https://www.cnblogs.com/zuoyang/p/17306704.html

相关文章

  • Go语言入门5(map哈希表)
    Map​ 哈希表是一种巧妙并且实用的数据结构。它是一个无序的key/value对的集合,其中所有的key都是不同的,然后通过给定的key可以在常数时间复杂度内检索、更新或删除对应的value。​ 在Go语言中,一个map就是一个哈希表的引用,map类型可以写为map[K]V,其中K和V分别对应key和value。m......
  • go 总汇
    命令作用gomodinit 生成go.mod文件gomoddownload 下载go.mod文件中指明的所有依赖gomodtidy 整理现有的依赖gomodgrap 查看现有的依赖结构gomodedit 编辑go.mod文件gomodvendo 导出项目所有的依赖到vendor目录gomodverify 校验一个模块是否被篡改过gomodwh......
  • 【go】文件
    file与base64互转packagemainimport( "encoding/base64" "fmt" "io/ioutil")funcmain(){ //file转base64 fileBytes,err:=ioutil.ReadFile("E:\\测试\\test.png")//读取file iferr!=nil{ panic(err) } ......
  • .NET开发工程师面试题
     一个网友参加了某公司的.NET开发工程师面试。该公司正在招聘一位薪资水平在20K-25k之间的优秀.NET开发工程师。为了帮助大家更好地了解.NET开发领域的要求和应试技巧,小编将与大家分享这个职位的面试题目。题目如下,大家先自己模拟回答一下,然后再看后面的答案。题目请简述.NET......
  • Studio 3T 2023.3 (macOS, Linux, Windows) - MongoDB 的专业 GUI、IDE 和 客户端,现在
    TheprofessionalGUI,IDEandclientforMongoDB请访问原文链接:https://sysin.org/blog/studio-3t-2023/,查看最新版。原创作品,转载请保留出处。作者主页:sysin.orgStudio3T,MongoDB的专业GUI、IDE和客户端适用于MongoDB的所有IDE、客户端和GUI工具——在Atlas......
  • go语言学习-gin框架路由
    表单参数表单参数传输为post请求,http常见的传输格式为四种application/jsonapplication/x-www-form-urlencodedapplication/xmlmultipart/form-data表单参数可以通过PostForm()方法获取,该方法默认解析的是x-www-form-urlencoded或from-data格式的参数<!DOCTYPEhtml><htmllang="e......
  • .NET Core MongoDB数据仓储和工作单元模式实操
    前言MongoDB从入门到实战的相关教程YyFlight.ToDoList项目源码地址MongoDB事务使用前提说明创建EntityBase公共类添加UserInfo用户表实体映射模型创建用户Repository创建用户管理业务代码UserOperationExample控制创建注册数据库基础操作和工作单元注册相关应用服务......
  • js相关面试题
    1.js的基础类型有什么?基础类型有:null,NaN,string,number,boolean,bigint,symbol,undefine引用类型有:object,Array,function2.tyopef和instanceof的区别:1.typeof可以识别所有的值类型,识别函数,能区分是否是引用类型consta="str" console.log(typeofa)  //stringconstb=999 c......
  • Django 同一Model注册多个modelAdmin
    需求:同一个djangomodel模型,根据不同需求展示注册到admin.py中classUserMsg(models.Model):username=models.CharField(max_length=20,null=False,verbose_name='发送方')hername=models.CharField(max_length=20,null=True,verbose_name='对方姓名')ti......
  • Go笔记(二):条件控制语句
    Go语言中的if语句根据条件表达式的结果选择需要执行的业务流程。1、if控制语句1、if语法语法详情如下:if条件表达式{//条件表达式为true,执行的代码块}条件表达式必须返回布尔型的结果,与Java语法不同,在Go中,if的条件表达式不使用括号。2、if/else语法......