Go语言切片详解
来源:云海天教程
时间:2022-12-29 10:28:34 398浏览 收藏
本篇文章向大家介绍《Go语言切片详解》,主要包括容器,具有一定的参考价值,需要的朋友可以参考一下。
切片(slice)是对数组的一个连续片段的引用,所以切片是一个引用类型(因此更类似于 C/C++ 中的数组类型,或者 Python 中的 list 类型),这个片段可以是整个数组,也可以是由起始和终止索引标识的一些项的子集,需要注意的是,终止索引标识的项不包括在切片内。Go语言中切片的内部结构包含地址、大小和容量,切片一般用于快速地操作一块数据集合,如果将数据集合比作切糕的话,切片就是你要的“那一块”,切的过程包含从哪里开始(切片的起始位置)及切多大(切片的大小),容量可以理解为装切片的口袋大小,如下图所示。
图:切片结构和内存分配
从数组或切片生成新的切片
切片默认指向一段连续内存区域,可以是数组,也可以是切片本身。从连续内存区域生成切片是常见的操作,格式如下:
slice [开始位置 : 结束位置]
语法说明如下:slice:表示目标切片对象;开始位置:对应目标切片对象的索引;结束位置:对应目标切片的结束索引。
从数组生成切片,代码如下:
var a = [3]int{1, 2, 3}fmt.Println(a, a[1:2])其中 a 是一个拥有 3 个整型元素的数组,被初始化为数值 1 到 3,使用 a[1:2] 可以生成一个新的切片,代码运行结果如下:
[1 2 3] [2]
其中 [2] 就是 a[1:2] 切片操作的结果。从数组或切片生成新的切片拥有如下特性:取出的元素数量为:结束位置 - 开始位置;取出元素不包含结束位置对应的索引,切片最后一个元素使用 slice[len(slice)] 获取;当缺省开始位置时,表示从连续区域开头到结束位置;当缺省结束位置时,表示从开始位置到整个连续区域末尾;两者同时缺省时,与切片本身等效;两者同时为 0 时,等效于空切片,一般用于切片复位。
根据索引位置取切片 slice 元素值时,取值范围是(0~len(slice)-1),超界会报运行时错误,生成切片时,结束位置可以填写 len(slice) 但不会报错。
下面通过实例来熟悉切片的特性。
1) 从指定范围中生成切片
切片和数组密不可分,如果将数组理解为一栋办公楼,那么切片就是把不同的连续楼层出租给使用者,出租的过程需要选择开始楼层和结束楼层,这个过程就会生成切片,示例代码如下:var highRiseBuilding [30]intfor i := 0; i 代码输出如下:
[11 12 13 14 15]
[21 22 23 24 25 26 27 28 29 30]
[1 2]
代码说明如下:第 8 行,尝试出租一个区间楼层。第 11 行,出租 20 层以上。第 14 行,出租 2 层以下,一般是商用铺面。
切片有点像C语言里的指针,指针可以做运算,但代价是内存操作越界,切片在指针的基础上增加了大小,约束了切片对应的内存区域,切片使用中无法对切片内部的地址和大小进行手动调整,因此切片比指针更安全、强大。
2) 表示原有的切片
生成切片的格式中,当开始和结束位置都被忽略时,生成的切片将表示和原切片一致的切片,并且生成的切片与原切片在数据内容上也是一致的,代码如下:a := []int{1, 2, 3}fmt.Println(a[:])a 是一个拥有 3 个元素的切片,将 a 切片使用 a[:] 进行操作后,得到的切片与 a 切片一致,代码输出如下:
[1 2 3]
3) 重置切片,清空拥有的元素
把切片的开始和结束位置都设为 0 时,生成的切片将变空,代码如下:a := []int{1, 2, 3}fmt.Println(a[0:0])代码输出如下:
[]
直接声明新的切片
除了可以从原有的数组或者切片中生成切片外,也可以声明一个新的切片,每一种类型都可以拥有其切片类型,表示多个相同类型元素的连续集合,因此切片类型也可以被声明,切片类型声明格式如下:var name []Type
其中 name 表示切片的变量名,Type 表示切片对应的元素类型。下面代码展示了切片声明的使用过程:
// 声明字符串切片var strList []string// 声明整型切片var numList []int// 声明一个空切片var numListEmpty = []int{}// 输出3个切片fmt.Println(strList, numList, numListEmpty)// 输出3个切片大小fmt.Println(len(strList), len(numList), len(numListEmpty))// 切片判定空的结果fmt.Println(strList == nil)fmt.Println(numList == nil)fmt.Println(numListEmpty == nil)代码输出结果:
[] [] []
0 0 0
true
true
false
{}
中填充切片的初始化元素,这里没有填充,所以切片是空的,但是此时的 numListEmpty 已经被分配了内存,只是还没有元素。第 11 行,切片均没有任何元素,3 个切片输出元素内容均为空。第 14 行,没有对切片进行任何操作,strList 和 numList 没有指向任何数组或者其他切片。第 17 行和第 18 行,声明但未使用的切片的默认值是 nil,strList 和 numList 也是 nil,所以和 nil 比较的结果是 true。第 19 行,numListEmpty 已经被分配到了内存,但没有元素,因此和 nil 比较时是 false。切片是动态结构,只能与 nil 判定相等,不能互相判定相等。
声明新的切片后,可以使用append()函数向切片中添加元素。
使用 make() 函数构造切片
如果需要动态地创建一个切片,可以使用 make() 内建函数,格式如下:make( []Type, size, cap )
其中 Type 是指切片的元素类型,size 指的是为这个类型分配多少个元素,cap 为预分配的元素数量,这个值设定后不影响 size,只是能提前分配空间,降低多次分配空间造成的性能问题。示例如下:
a := make([]int, 2)b := make([]int, 2, 10)fmt.Println(a, b)fmt.Println(len(a), len(b))代码输出如下:
[0 0] [0 0]
2 2
容量不会影响当前的元素个数,因此 a 和 b 取 len 都是 2。
温馨提示
使用 make() 函数生成的切片一定发生了内存分配操作,但给定开始与结束位置(包括切片复位)的切片只是将新的切片结构指向已经分配好的内存区域,设定开始与结束位置,不会发生内存分配操作。今天关于《Go语言切片详解》的内容介绍就到此结束,如果有什么疑问或者建议,可以在golang学习网公众号下多多回复交流;文中若有不正之处,也希望回复留言以告知!
-
493 收藏
-
133 收藏
-
496 收藏
-
495 收藏
-
242 收藏
-
321 收藏
-
303 收藏
-
245 收藏
-
422 收藏
-
405 收藏
-
280 收藏
-
- 前端进阶之JavaScript设计模式
- 设计模式是开发人员在软件开发过程中面临一般问题时的解决方案,代表了最佳的实践。本课程的主打内容包括JS常见设计模式以及具体应用场景,打造一站式知识长龙服务,适合有JS基础的同学学习。
- 立即学习 542次学习
-
- GO语言核心编程课程
- 本课程采用真实案例,全面具体可落地,从理论到实践,一步一步将GO核心编程技术、编程思想、底层实现融会贯通,使学习者贴近时代脉搏,做IT互联网时代的弄潮儿。
- 立即学习 507次学习
-
- 简单聊聊mysql8与网络通信
- 如有问题加微信:Le-studyg;在课程中,我们将首先介绍MySQL8的新特性,包括性能优化、安全增强、新数据类型等,帮助学生快速熟悉MySQL8的最新功能。接着,我们将深入解析MySQL的网络通信机制,包括协议、连接管理、数据传输等,让
- 立即学习 497次学习
-
- JavaScript正则表达式基础与实战
- 在任何一门编程语言中,正则表达式,都是一项重要的知识,它提供了高效的字符串匹配与捕获机制,可以极大的简化程序设计。
- 立即学习 487次学习
-
- 从零制作响应式网站—Grid布局
- 本系列教程将展示从零制作一个假想的网络科技公司官网,分为导航,轮播,关于我们,成功案例,服务流程,团队介绍,数据部分,公司动态,底部信息等内容区块。网站整体采用CSSGrid布局,支持响应式,有流畅过渡和展现动画。
- 立即学习 484次学习
-
- 传统的书本
- 这篇博文真是及时雨啊,细节满满,很棒,码起来,关注作者大大了!希望作者大大能多写Golang相关的文章。
- 2023-02-24 10:34:08
-
- 冷艳的蜗牛
- 太细致了,已加入收藏夹了,感谢up主的这篇技术贴,我会继续支持!
- 2023-02-15 16:39:24
-
- 甜蜜的水壶
- 很有用,一直没懂这个问题,但其实工作中常常有遇到...不过今天到这,帮助很大,总算是懂了,感谢师傅分享技术贴!
- 2023-02-12 09:04:38
-
- 俏皮的画板
- 这篇文章真及时,细节满满,很有用,已加入收藏夹了,关注作者大大了!希望作者大大能多写Golang相关的文章。
- 2023-02-01 03:13:23
-
- 还单身的柜子
- 这篇文章真及时,大佬加油!
- 2023-01-23 10:32:25
-
- 清脆的柠檬
- 写的不错,一直没懂这个问题,但其实工作中常常有遇到...不过今天到这,看完之后很有帮助,总算是懂了,感谢楼主分享技术文章!
- 2023-01-22 15:37:04
-
- user_1671454250
- 很有用,一直没懂这个问题,但其实工作中常常有遇到...不过今天到这,帮助很大,总算是懂了,感谢楼主分享文章!
- 2023-01-15 10:24:24
-
- 传统的网络
- 太详细了,已收藏,感谢up主的这篇文章内容,我会继续支持!
- 2023-01-09 07:32:30
-
- 虚拟的小兔子
- 这篇博文太及时了,太全面了,很棒,已加入收藏夹了,关注作者大大了!希望作者大大能多写Golang相关的文章。
- 2023-01-08 05:47:18