Golang new() vs make()
对于Golang的new() 和 make()的用法有些混乱,感觉这篇资料讲解较好,翻译一下,方便学习!
原文地址:http://www.godesignpatterns.com/2014/04/new-vs-make.html
本文简要阐述Go语言中内建函数new()和make()的区别,主要面向Go语言的菜鸟:-)
内建函数new(T)为一个类型T的新变量分配内存空间,值为零,并以该空间的地址作为函数的返回值,返回值类型为*T。按照Go的说法,它返回一个指针,指向新开辟的T类型的零值。例如,有三种方式建立一个指向bytes.Buffer类型值为0的指针p,结果相同:
// 分配足够的内存空间存放bytes.Buffer类型的value,返回指向value地址的指针
var buf bytes.Buffer
p := &buf // 使用一个复合字面量分配内存给value,返回指向value地址的指针
p := &bytes.Buffer{} // 使用new函数实现上面的功能
p := new(bytes.Buffer)
然而,与new()不同,make()作为特殊的内建函数,被用于初始化slices、maps、channels。
值得注意的是make() 只能用于初始化slices、maps、channels。不像new()函数,make()不能返回一个指针。
slices、maps和channels使用复合字面量进行初始化或make()均可。下面以两种不同的方式(结果一样)初始化map m,m的keys为string,values为bool:
// 使用make() 初始化 一个map
m := make(map[string]bool, ) // 使用复合字面量初始化map
m := map[string]bool{}
你也可以使用带有初始化数据的复合字面量初始化maps,如下所示:
m := map[string]bool{
"java": false,
"go": true,
}
new()的作用比较明了,make()仍然难以理解,继续看下这里https://golang.org/doc/effective_go.html#allocation_make
内建函数make(T, args)与new(T)的使用目的不同。它仅用于初始化slices、maps、channels,并返回一个初始化(非零)的T类型(不是*T)值。造成这种差异的原因是,这三种类型,表层下面,代表的是对数据结构的引用,以至于使用前必须初始化。例如,一个slice是包含三项的描述符,其中一项是一个指针,指向数据(array里面的),另外两项分别是length和capacity。直到这些项被初始化之前,slice是nil。对于slice、maps和channels,make 初始化内部数据结构,准备可用的值。举个例子:
make([]int, , )
创建一个包含100个整数的array,然后生成一个slice 结构,length为10,capacity为100, 指向array起始的10个元素。相反,new([]int)返回一个新生成的指针,零值的slice,也就是说该指针指向一个nil的slice值。
这些例子阐明了new和make的不同。
var p *[]int = new([]int) //创建一个slice结构;*p == nil;很少使用
var v []int = make([]int, ) //slice v 引用了一个新的含有100个元素的array //费力不讨好,可以这么写:
var p *[]int = new([]int)
*p = make([]int, , ) //地道的写法:
v := make([]int, )
记住,make仅用于slices、maps、channels;想要获得确切的指针就用new,或者显示获取变量的地址。
=============================================================
总结一下:
1. 使用对象不同,make()只用于初始化话slices、maps、channels;
2. 返回结果不同,new()返回的是指针。
Golang new() vs make()的更多相关文章
- Golang, 以17个简短代码片段,切底弄懂 channel 基础
(原创出处为本博客:http://www.cnblogs.com/linguanh/) 前序: 因为打算自己搞个基于Golang的IM服务器,所以复习了下之前一直没怎么使用的协程.管道等高并发编程知识 ...
- 说说Golang的使用心得
13年上半年接触了Golang,对Golang十分喜爱.现在是2015年,离春节还有几天,从开始学习到现在的一年半时间里,前前后后也用Golang写了些代码,其中包括业余时间的,也有产品项目中的.一直 ...
- TODO:Golang指针使用注意事项
TODO:Golang指针使用注意事项 先来看简单的例子1: 输出: 1 1 例子2: 输出: 1 3 例子1是使用值传递,Add方法不会做任何改变:例子2是使用指针传递,会改变地址,从而改变地址. ...
- Golang 编写的图片压缩程序,质量、尺寸压缩,批量、单张压缩
目录: 前序 效果图 简介 全部代码 前序: 接触 golang 不久,一直是边学边做,边总结,深深感到这门语言的魅力,等下要跟大家分享是最近项目 服务端 用到的图片压缩程序,我单独分离了出来,做成了 ...
- golang struct扩展函数参数命名警告
今天在使用VSCode编写golang代码时,定义一个struct,扩展几个方法,如下: package storage import ( "fmt" "github.c ...
- golang语言构造函数
1.构造函数定义 构造函数 ,是一种特殊的方法.主要用来在创建对象时初始化对象, 即为对象成员变量赋初始值,总与new运算符一起使用在创建对象的语句中.特别的一个类可以有多个构造函数 ,可根据其参数个 ...
- TODO:Golang语言TCP/UDP协议重用地址端口
TODO:Golang语言TCP/UDP协议重用地址端口 这是一个简单的包来解决重用地址的问题. go net包(据我所知)不允许设置套接字选项. 这在尝试进行TCP NAT时尤其成问题,其需要在同一 ...
- golang的安装
整理了一下,网上关于golang的安装有三种方式(注明一下,我的环境为CentOS-6.x, 64bit) 方式一:yum安装(最简单) rpm -Uvh http://dl.fedoraprojec ...
- golang枚举类型 - iota用法拾遗
在c#.java等高级语言中,经常会用到枚举类型来表示状态等.在golang中并没有枚举类型,如何实现枚举呢?首先从枚举的概念入手. 1.枚举类型定义 从百度百科查询解释如下:http://baike ...
- golang 使用 iota
iota是golang语言的常量计数器,只能在常量的表达式中使用. iota在const关键字出现时将被重置为0(const内部的第一行之前),const中每新增一行常量声明将使iota计数一次(io ...
随机推荐
- vue 源码分析
初始化 Data,props,event监听 beforCreated,Created 挂载 执行编译,首次渲染.创建和追加过程 编译 编译模块分为三个阶段:parse.optimize.gener ...
- 53. Maximum Subarray (JAVA)
iven an integer array nums, find the contiguous subarray (containing at least one number) which has ...
- Nginx中配置https中引用http的问题
Nginx中配置https中引用http的问题 遇到问题: 今天公司要在后台增加直播入口,使用腾讯云的实时音视频,要求是必须使用https,在配置完强制跳转https候,发现后台无法上传图片,在浏览器 ...
- Tomcat启动慢的原因及解决方法
Tomcat启动慢的原因及解决方法 在CentOS启动Tomcat时,启动过程很慢,需要几分钟,经过查看日志,发现耗时在这里:是session引起的随机数问题导致的.Tocmat的Session ID ...
- 对 django rest framework框架的认识
- 路由 - 可以通过as_view传参数,根据请求方式不同执行相应的方法 - 可以在url中设置一个结尾,类似于: .json - 视图 - 帮助开发者提供了一些类,并在类中提供了多个方法以供我们使 ...
- Docker下载镜像并创建容器运行
在linux系统中安装完成docker后,我们开始进行docker的镜像.容器的使用. 在使用docker时,首先要明确的两个概念:image(镜像) 与 container (容器) image: ...
- python time、datetime模块
时间的三种格式:1)时间戳 2)格式化的时间字符串 3)元组(struct_time):time.struct_time(tm_year=1970, tm_mon=5, tm_mday=23, tm_ ...
- 左半连接left demi-join
返回左边表的记录,前提是其记录对于右边表满足on语句的判定条件 对于左表中一条指定的记录,在右表中一旦找到匹配的记录,hive就会立即停止扫描 1.sql select s.myd,s,symbol, ...
- python笔记(3)---列表
lst = ["bob","jack","马云","马化腾","王健林"] del lst[1:3] ...
- 一个简单SpringBoot应用的pom.xml文件
<?xml version="1.0" encoding="UTF-8"?> <project xmlns="http://mave ...