golang指针相关

指针相关的部分实在是没有搞太明白,抽时间来总结下。

1.指针相关基础知识
比如现在有一句话:『谜底666』,这句话在程序中一启动,就要加载到内存中,假如内存地址0x123456,然后我们可以将这句话复制给变量A,这句话的地址复制给变量B,首先变量B就是一个指针变量。
& 运算符:用于取地址
*运算符:用于根据地址取值
PS:地址是干嘛的:每个变量在运行是都有一个地址,这个地址代表该变量在内存中的位置

func main() {
	a := 10
	b := &a //取地址  等同于 var b *int = &a  此时的*int 代表变量b是一个*int类型
	fmt.Printf("a:%d ptr:%p\n", a, &a) // a:10 ptr:0xc00001a078
	fmt.Printf("b:%p type:%T\n", b, b) // b:0xc00001a078 type:*int
	fmt.Println(&b)                    // 0xc00000e018 取b的地址(b本身也是一个指针类型)
}

放一张图:
在这里插入图片描述
对普通变量使用&操作符取地址的话,会得到这个变量的指针,然后可以用*操作符进行指针取值。

func main() {
	//指针取值
	a := 10
	b := &a // 取变量a的地址,将指针保存到b中
	fmt.Printf("type of b:%T\n", b)
	c := *b // 指针取值(根据指针去内存取值)
	fmt.Printf("type of c:%T\n", c)
	fmt.Printf("value of c:%v\n", c)
}
输出如下:
type of b:*int
type of c:int
value of c:10

再来个例子:

package main

import "fmt"

func main() {
	var (
		a int = 100
		b int = 300
	)
	fmt.Printf("交换前a的值: %d\n", a)
	fmt.Printf("交换前b的值: %d\n\n", b)

	swap(&a, &b)

	fmt.Printf("交换后a的值: %d\n", a)
	fmt.Printf("交换后b的值: %d\n", b)
}

func swap(x, y *int) {
	//值传递,两数交换
	*x, *y = *y, *x
}
//输出结果如下
交换前a的值: 100
交换前b的值: 300

交换后a的值: 300
交换后b的值: 100

小结:

  • 对变量进行取地址(&)操作,可以获得这个变量的指针变量。
  • 指针变量的值是指针地址。
  • 对指针变量进行取值(*)操作,可以获得指针变量指向的原变量的值。

2.如何进行指针传值

func modify1(x int) {
	x = 100
}
func modify2(x *int) {   //表示x是一个*int类型
	*x = 100   //对变量x取值后,赋值100,由于在主函数传的是变量a的地址,所以相当于对a赋值100
}
func main() {
	a := 10
	modify1(a)
	fmt.Println(a) // 10  不改变,
	modify2(&a)
	fmt.Println(a) // 100
}

上述代码也可以这样操作:

func modify3(x int) int{
    x = 100
    return x
}

func main() {
    a := 10
    a = modify3(a)  // 这里虽然都叫a,但是内存地址是不一样的
    fmt.Println(a) // 100
}

再来一个栗子:

func main() {
	a := 10
	pointerDemo03(&a)
	fmt.Println(a)
}

// 注意,指针作为函数的时候,参数也要加上*
func pointerDemo03(a *int) {
	*a = 20
}
//到现在位置应该明白了,不用再赘述这个了

3.new(不太在实际项目中见到)
使用new函数得到的是一个类型的指针,并且该指针对应的值为该类型的零值,每次调用 new 函数都会返回唯一的地址变量(当定义一个空 struct 时,通过 new 创建一个变量时,返回的地址是相同的。):

func main() {
	a := new(int)
	b := new(bool)
	fmt.Printf("%T\n", a) // *int
	fmt.Printf("%T\n", b) // *bool
	fmt.Println(*a)       // 0
	fmt.Println(*b)       // false
}

关于new函数再举一个栗子:

func main() {
    // 创建一个未命名的 int 类型变量,初始值是 0,返回值 p 是指向 int 类型变量的指针。
    p := new(int)
    fmt.Println(p, *p) // 0xc00001c0b8 0
    // 创建一个未命名的 string 类型变量,初始值是 "", 返回值是 q 是指向 string 类型变量的指针。
    q := new(string)
    fmt.Println(q, *q) // 0xc000010240 ""

    *q = "a"
    fmt.Println(*q) // a
}

make
make也是用于内存分配的,区别于new,它只用于slice、map以及chan的内存创建,而且它返回的类型就是这三个类型本身,而不是他们的指针类型,因为这三种类型就是引用类型,所以就没有必要返回他们的指针了

4.数组指针与指针数组
指针数组是指元素为指针类型的数组,数组指针是获取数组变量的地址
数组指针:

func pointerDemo05() {
	arr := [10]int{1, 2, 3, 3, 4, 5}
	var p *[10]int  //定义p是一个数组指针
	p = &arr        //对这个数组指针赋值,赋值的是变量arr的地址
	fmt.Println(*p)      // 获取数组中的全部数据
	fmt.Println((*p)[0]) // 获取指定数组中索引的数据,因为*p是先运算,所以要先加括号,否则编译报错
	fmt.Println(p[0])    // 获取指定数组中索引的数据,这个格式和加括号一样,但是简化的写法

	for i := 0; i < len(p); i++ {
		fmt.Print(p[i], ",")
	}
}

指针数组:元素为指针类型的数组

func pointerDemo07() {
	var p [2]*int //注意和上面的区别
	a := 10
	b := 20
	// 变量a的内存地址保存在指针数组p的0索引,b保存在1索引
	p[0] = &a
	p[1] = &b
	fmt.Println(p)            // 获取p数组中的内存地址
	fmt.Println(*p[0], *p[1]) // 获取p数组中的指定索引数据

	for i := 0; i < len(p); i++ {
		fmt.Println(*p[i]) // 获取p数组中的所有的数据
	}

	for key, value := range p {
		fmt.Println(key, *value)
	}
}

5.结构体指针
直接使用结构体的方式(用new):

type People struct{
    Name string
    Age int
}

peo := new(People)
//因为结构体本质是值类型,所以创建结构体指针时已经开辟了内存空间
fmt.Println(peo == nil) //输出:false
//由于结构体中属性并不是指针类型,所以可以直接调用
peo.Name = "jeff"
fmt.Println(peo)//输出:&{jeff 0}
peo1:=peo
peo1.Name="高级语言"
fmt.Println(peo1,peo)//输出:&{高级语言 0} &{高级语言 0}

也可以声明结构体指针来进行赋值:

//声明结构体指针
var peo *People   //表示变量peo是一个*People类型(结构体指针类型)
//给结构体指针赋值
peo = &People{"jeff", 18}
/*
上面代码使用短变量方式如下
peo:= &People{"jeff", 18}
 */
fmt.Println(peo)

结构体指针比较的是地址,*结构体指针取出地址中对应的值

p1 := People{"jeff", 18}
p2 := People{"jeff", 18}
fmt.Printf("%p %p\n", &p1, &p2) //输出地址不同
fmt.Println(p1 == p2)           //输出:true

p3 := new(People)
p3 = &People{"jeff", 18}
//结构体变量不能和指针比较,使用*指针取出地址中值
fmt.Println(p1 == *p3) //输出:true

p4 := &People{"jeff", 18}
//指针比较的是地址
fmt.Println(p3 == p4) //输出:false

PS:使用new来初始化结构体后,得到的是结构体的地址,栗子如上
再来一个栗子:

type Student struct {
	// 成员名称不加var关键字
	id   int
	name string
	age  int
	addr string
}
func main() {
	stu := Student{001, "itzhuzhu", 23, "广州"}
	var p *Student
	p = &stu
	pointerDemo10(p)
	fmt.Println(stu)
}

func pointerDemo10(p *Student) {
	p.addr = "深圳"
}
//输出结果为{1 itzhuzhu 23 深圳}

下面这个同上面:

func main() {
	stu := Student{001, "itzhuzhu", 23, "广州"}
	//var p *Student
	//p = &stu
	pointerDemo10(&stu)
	fmt.Println(stu)
}

func pointerDemo10(p *Student) {
	p.addr = "深圳"
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mfbz.cn/a/10281.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

多线程(八):常见锁策略

目录 前言 1. 乐观锁 VS 悲观锁 乐观锁 悲观锁 2. 轻量级锁 VS 重量级锁 轻量级锁 3. 自旋锁 VS 挂起等待锁 自旋锁 挂起等待锁 4. 读写锁 VS 互斥锁 5. 可重入锁 vs 不可重入锁 死锁 发生死锁的情况 死锁产生的四个必要条件如下&#xff1a; 6. 公平锁和非公平锁…

【Java EE】-多线程编程(九) 锁策略CAS锁优化

作者&#xff1a;学Java的冬瓜 博客主页&#xff1a;☀冬瓜的主页&#x1f319; 专栏&#xff1a;【JavaEE】 分享&#xff1a; 主要内容&#xff1a;乐观锁VS悲观锁、轻量级锁VS重量级锁、自旋锁VS挂起等待锁、互斥锁VS读写锁、公平锁VS非公平锁、可重入锁VS不可重入锁。CAS实…

Python数据结构与算法-树

一、树的概念详情见 https://blog.csdn.net/little_limin/article/details/129845592 Python数据结构与算法-堆排序&#xff08;NB组&#xff09;—— 一、树的基础知识二、树的实例&#xff1a;模拟文件系统1、树的存储树结构也是链式存储的&#xff0c;与链表的结构相似&…

类ChatGPT代码级解读:如何从零起步实现Transformer、llama/ChatGLM

前言 最近一直在做类ChatGPT项目的部署 微调&#xff0c;关注比较多的是两个&#xff1a;一个LLaMA&#xff0c;一个ChatGLM&#xff0c;会发现有不少模型是基于这两个模型去做微调的&#xff0c;说到微调&#xff0c;那具体怎么微调呢&#xff0c;因此又详细了解了一下微调代…

Vulnhub_Pylington

目录 一、信息收集 &#xff08;一&#xff09;端口服务探测 &#xff08;二&#xff09;目录扫描 二、漏洞挖掘 &#xff08;一&#xff09;robots敏感信息泄露 &#xff08;二&#xff09;python IDE沙箱绕过RCE 1. python敏感函数沙盒绕过 2. exec(__import_…

【ES】搜索结果处理RestClient查询文档

【ES】搜索结果处理&RestClient查询文档2.搜索结果处理2.1.排序2.1.1.普通字段排序2.1.2.地理坐标排序2.2.分页2.2.1.基本的分页2.2.2.深度分页问题2.2.3.小结2.3.高亮2.3.1.高亮原理2.3.2.实现高亮2.4.总结3.RestClient查询文档3.1.快速入门3.1.1.发起查询请求3.1.2.解析响…

Python做个猫狗识别系统,给人美心善的邻居

嗨害大家好鸭&#xff01;我是爱摸鱼的芝士❤ 宠物真的看着好治愈 谁不想有一只属于自己的乖乖宠物捏~ 这篇文章中我放弃了以往的model.fit()训练方法&#xff0c; 改用model.train_on_batch方法。 两种方法的比较&#xff1a; model.fit()&#xff1a;用起来十分简单&#…

Kubernetes 部署 StarRocks 集群

文章目录StarRocks简介系统架构图安装部署StarRocks手动部署通过 Docker部署使用 StarGo 部署管理通过 StarRocks Manager部署管理通过 Kubernetes部署工作原理逻辑图部署 StarRocks Operator部署 StarRocks 集群访问 StarRocks 集群集群内访问 StarRocks 集群集群外访问 StarR…

【案例实践】R语言多元数据统计分析在生态环境中的实践应用

查看原文>>>R语言生物群落分析绘图、多元统计分析、CMIP6、遥感碳储量、GEE林业、InVEST等 生态环境领域研究中常常面对众多的不同类型的数据或变量&#xff0c;当要同时分析多个因变量&#xff08;y&#xff09;时需要用到多元统计分析&#xff08;multivariate sta…

Spark----DataFrame和DataSet

Spark之DataFrame和DataSet 文章目录Spark之DataFrame和DataSetDataFrameDSL 语法创建DataFrame查看DataFrame的Schema信息只查看列数据的6种方式按照“age”分区&#xff0c;查看数据条数增加列withColumn修改列名withColumnRenamedRDD 转换为 DataFrameDataFrame 转换为 RDD转…

音质蓝牙耳机哪款好用?2023公认音质好的四款蓝牙耳机推荐

现如今&#xff0c;蓝牙耳机越来越受欢迎&#xff0c;不少人在听歌、追剧、甚至是玩游戏的时候都会戴着它。最近看到很多人问&#xff0c;音质蓝牙耳机哪款好用&#xff1f;针对这个问题&#xff0c;我来给大家推荐四款公认音质好的蓝牙耳机&#xff0c;一起来看看吧。 一、南…

算法笔记:Frechet距离度量

曲线之间相似性的度量&#xff0c;它考虑了沿曲线的点的位置和顺序 1 概念 1.1 直观理解 主人走路径A&#xff0c;狗走路径B&#xff0c;他们有不同的配速方案主人和狗各自走完这两条路径过程中所需要的最短狗绳长度 &#xff08;在某一种配速下需要的狗绳长度&#xff09;&a…

考研复试确认神操作!

终于进行到了研究生考试的尾声&#xff0c;但让考生感到无力吐槽的事情&#xff0c;却还在继续上演&#xff0c;比如苏科大&#xff0c;再比如中地大、苏大&#xff0c;三所学校的神操作&#xff0c;着实让无数考生忍不住调侃&#xff1a;原来考研不仅拼实力&#xff0c;还得拼…

你的APP内存还在暴增吗?试着用Bitmap管理下内存~

作者&#xff1a;layz4android 相信伙伴们在日常的开发中&#xff0c;一定对图片加载有所涉猎&#xff0c;而且对于图片加载现有的第三方库也很多&#xff0c;例如Glide、coil等&#xff0c;使用这些三方库我们好像就没有啥担忧的&#xff0c;他们内部的内存管理和缓存策略做的…

如何实现Chatgpt写文章(附chatgpt3.5免费接口)

申明&#xff1a;本次只是说一下实现思路&#xff0c;官方的接口以及如何实现方式&#xff0c;本文没有提及&#xff0c;这次只是一个思路&#xff0c;若想代替人工完成质量还差的很远&#xff0c;请审核大大放行 今天再次优化了代码&#xff0c;修复了一些bug&#xff0c;考虑…

VUE 学习笔记(一)开发环境搭建

1、Visual Studio Code安装及使用 下载地址官网&#xff1a;https://code.visualstudio.com/ 直接点击下载按钮即可&#xff0c;会根据系统自动下载合适的版本&#xff0c;无需自行选择。 2、VSCode 上安装&#xff1a;JavaScript Debugger 目前 Debugger for Chrome 已经处…

使用向量机(SVM)算法的推荐系统部署实现

包括3个模块&#xff1a;数据预处理、模型训练及保存、模型测试&#xff0c;下面分别给出各模块的功能介绍及相关代码。 数据集下载链接为https://www.aitechclub.com/data-detail? data_id29&#xff0c;停用词典下载链接为http://www.datasoldier.net/archives/636。 1.数…

232:vue+openlayers选择左右两部分的地图,不重复,横向卷帘

第232个 点击查看专栏目录 本示例的目的是介绍演示如何在vue+openlayers项目中自定义js实现横向卷帘。这个示例中从左右两个选择框中来选择不同的地图,做了不重复的处理,即同一个数组,两部分根据选择后的状态做disabled处理,避免重复选择。 直接复制下面的 vue+openlayers…

c语言—指针进阶

创作不易&#xff0c;本篇文章如果帮助到了你&#xff0c;还请点赞支持一下♡>&#x16966;<)!! 主页专栏有更多知识&#xff0c;如有疑问欢迎大家指正讨论&#xff0c;共同进步&#xff01; 给大家跳段街舞感谢支持&#xff01;ጿ ኈ ቼ ዽ ጿ ኈ ቼ ዽ ጿ ኈ ቼ ዽ ጿ…

第13届蓝桥杯省赛真题剖析-2022年4月17日Scratch编程初中级组

[导读]&#xff1a;超平老师的《Scratch蓝桥杯真题解析100讲》已经全部完成&#xff0c;后续会不定期解读蓝桥杯真题&#xff0c;这是Scratch蓝桥杯真题解析第122讲。 第13届蓝桥杯省赛举办了两次&#xff0c;这是2022年4月17日举行的第一次省赛&#xff0c;比赛仍然采取线上形…
最新文章