go中值传递、引用传递、指针传递的区别
go语言中的值类型:
int、float、bool、array、sturct等
值传递是指在调用函数时将实际参数复制一份传递到函数中,这样在函数中如果对参数进行修改,将不会影响到实际参数
声明一个值类型变量时,编译器会在栈中分配一个空间,空间里存储的就是该变量的值
go语言中的引用类型:
slice,map,channel,interface,func,string等
声明一个引用类型的变量,编译器会把实例的内存分配在堆上
string和其他语言一样,是引用类型,string的底层实现struct String { byte* str; intgo len; }; 但是因为string不允许修改,每次操作string只能生成新的对象,所以在看起来使用时像值类型。
所谓引用传递是指在调用函数时将实际参数的地址传递到函数中,那么在函数中对参数所进行的修改,将影响到实际参数。
需要注意的是:引用类型在函数的内部可以对它的值进行修改,但是如果给形参重新赋值,重新赋值后的形参再怎么修改都不会影响外面的实参了
nil可以赋值给引用类型(除string外)、error类型和指针类型
go语言中的指针类型:
一个指针变量指向了一个值的内存地址
当一个指针被定义后没有分配到任何变量时,它的值为 nil。nil 指针也称为空指针
一个指针变量通常缩写为 ptr
其实引用类型可以看作对指针的封装
空指针判断:
if(ptr != nil) /* ptr 不是空指针 */
if(ptr == nil) /* ptr 是空指针 */
例子:
package main
import "fmt"
type pArr []int
func (p *pArr) oopFunc() {
(*p)[] =
}
type newFunc func(string)
func strFunc(s string) {
fmt.Printf("%T ", s[]) //uint8
fmt.Println(s) //hello world
}
type Person struct {
Name string
Height int
}
func changeStruct(p Person) {
p.Name = "李四"
p.Height =
}
func main() {
//切片指针的使用
var ptr []*int
i :=
ptr = append(ptr, &i)
fmt.Println("ptr:", *ptr[])
//结构体是值类型
person := Person{
"张三",
,
}
changeStruct(person)
fmt.Println(person) //{张三 180}
//func 可以作为参数进行传递
var nf newFunc
nf = strFunc
str := "hello world"
nf(str) //uint8 hello world
//类似面向对象的方法
p := make(pArr, )
p.oopFunc()
fmt.Println("p:", p) //p: [0 0 0 111]
//值类型无法被改变
num :=
valPass(num)
fmt.Println("num:", num) //num: 1
//引用类型可以在函数中被改变
nums := []int{, , , }
RefPass(nums)
fmt.Println("nums:", nums) //nums: [0 100 2 3]
//形参可以改变引用类型的值,但不能够形参重新赋值
RefPass2(nums)
fmt.Println("nums:", nums) //nums: [0 100 2 3]
//形参可以改变指针类型的值
n := new(int)
*n =
PointPass(n)
fmt.Println("n:", *n) //n: 12
//形参可以改变指针类型的值,但是对形参重新赋值,不会影响实参
PointPass2(n)
fmt.Println("n:", *n) //n: 12
}
//指针传递,对指针重新赋值,指针指向了新的地址,此时对形参做修改将不再影响外面的实参
func PointPass2(num *int) {
num = new(int)
*num =
}
// 指针传递,普通用法
func PointPass(num *int) {
*num =
}
//引用传递,普通用法,这个会改变外面的实参
func RefPass(nums []int) {
nums[] =
}
//引用传递,对形参重新赋值,不会改变外面的实参,形参指向了新的地址
func RefPass2(nums []int) {
nums = []int{, , , }
}
//值传递
func valPass(num int) {
num =
}
go中值传递、引用传递、指针传递的区别的更多相关文章
- c++值传递和引用及指针传递区别
以下程序各有何问题? ***************************************************************************************** ...
- Javascript参数传递中值和引用的一种理解
值(value)和引用(reference)是各种编程语言老生常谈的话题,js也不例外. 我将剖析一个例子的实际运行过程,跟大家分享我对js参数传递中的值和引用的理解. 参考官网数据类型的两种分类,本 ...
- 传参数应该用哪种形式——值、引用、指针?
类型:C++ & Qt4,创建时间:十二月 30, 2011, 7:43 p.m. 标题无"转载"即原创文章,版权所有.转载请注明来源:http://hgoldfish.c ...
- C#中值和引用
c#中有两种基本类型,它们分别是值类型和引用类型:而每种类型都可以细分为如下类型: ps:1.基本类型是值类型 2.类.接口.委托都是引用类型
- C++中值传递、指针传递、引用传递的总结
C++中值传递.指针传递.引用传递的总结 指针传递和引用传递一般适用于:函数内部修改参数并且希望改动影响调用者.对比值传递,指针/引用传递可以将改变由形参"传给"实参(实际上就 ...
- c++中值传递,址传递,引用传递
概念详解 1. 值传递: 形参是实参的拷贝,改变形参的值并不会影响外部实参的值. 从被调用函数的角度来说,值传递是单向的(实参->形参),参数的值只能传入,不能传出: 当函数内部需要修改参数,并 ...
- java中值传递和引用传递
最近工作中使用到了值传递和引用传递,但是有点懵,现在看了下面的文章后清晰多了.一下是文章(网摘) 1:按值传递是什么 指的是在方法调用时,传递的参数是按值的拷贝传递.示例如下: public clas ...
- C++指针传递和引用传递的区别 (转载整理)
区别1:指针传递和引用传递是以不同的方式实现相同的效果,但是指针传递的本质还是值传递,只是传递的值是地址. 就拿 交换两个数的函数来举例: // 指针传递 void swap(int * val1, ...
- C语言指针传递详解
传递指针可以让多个函数访问指针所引用的对象,而不用把对象声明为全局可访问,要在某个函数中修改数据,需要用指针传递数据,当数据是需要修改的指针的时候,就要传递指针的指针,传递参数(包括指针)的时候,传递 ...
- C++中引用和指针详解
先来分析指针这个东东: 从概念上讲,指针本质上就是存放变量地址的一个变量,在逻辑上是独立的,它可以被改变,包括其所指向的地址的改变和其指向的地址中所存放的数据的改变. 上面的图表示了程序运行时变量的值 ...
随机推荐
- 20180516模拟赛T2——string
题解 对于一个字符串A,我们只能把其首字符取出,故如果我们想让A串与B串相等,能重复利用的部分只能是A串结尾与B串开头相等的部分.对于取出的字符,我们可以把'o'放在一个容器中,把'x'放在另一个容器 ...
- python - 将天数转换成日期
# 如果是 0 则为今天 def getdate(day): today = datetime.datetime.now() deviation = datetime.timedelta(days=- ...
- 删除ubuntu旧内核的方法
https://www.jianshu.com/p/75edb9a5fbab 磁盘满了 需要清理系统盘 1,先用uname -a 查看当前内核版本: uname -a Linux 10-9-37-13 ...
- ABP 01 项目的基本运行
原文:https://www.cnblogs.com/ldybyz/p/8441084.html 照着这篇文章弄 一般是没有什么问题的 记录一下我出现的问题,大多是没有仔细看文章. 1.无法迁移数据库 ...
- #Ubuntu 14.04 系统下载
http://mirrors.aliyun.com/ubuntu-releases/14.04/
- JavaScript 整数转大写中文
function toChinese(money){ var chNum=['零','壹','贰','叁','肆','伍','陆','柒','捌','玖']; var maxnum=999999999 ...
- [原创]浅谈对任务分解法WBS应用
[原创]浅谈对任务分解法WBS应用 1.WBS是什么? 即Work Breakdown Structure如何进行WBS分解:目标→任务→工作→活动 2.WBS分解的原则:将主体目标逐步细化分解,最底 ...
- Http、Socket、WebSocket之间联系与区别
WebSocket和Socket区别 可以把WebSocket想象成HTTP(应用层),HTTP和Socket什么关系,WebSocket和Socket就是什么关系. HTTP 协议有一个缺陷:通信只 ...
- Django实现自动发布(1数据模型)
公司成立之初,业务量较小,一个程序包揽了所有的业务逻辑,此时服务器数量少,上线简单,基本开发-测试-上线都是由开发人员完成. 随着业务量逐渐上升,功能增多,代码量增大,而单一功能上线需要重新编译整个程 ...
- SpringBoot(十七):SpringBoot2.1.1数据类型转化器Converter
什么场景下需要使用类型化器Converter? springboot2.1.1在做Restful Api开发过程中往往希望接口直接接收date类型参数,但是默认不加设置是不支持的,会抛出异常:系统是希 ...