Go语言中底层数组和切片的关系以及数组扩容规则
Go语言中底层数组和切片的关系以及数组扩容规则
demo
package main
import (
"fmt"
)
func main() {
// 声明一个底层数组,长度为10,容量为10
arr := []int {0,1,2,3,4,5,6,7,8,9}
fmt.Printf("[%T]len(arr)=%d,cap(arr)=%d \n",arr,len(arr),cap(arr))
// 声明两个切片,分别取底层数组的[1,4],[7:]
s1 := arr[1:4]
fmt.Printf("[%T]len(s1)=%d,cap(s1)=%d \n",s1,len(s1),cap(s1))
s2 := arr[7:]
fmt.Printf("[%T]len(s2)=%d,cap(s2)=%d \n",s2,len(s2),cap(s2))
// 数组越界指的是超出数组长度,例如下面报:panic: runtime error: index out of range [3] with length 3
//fmt.Println(s1[3])
// s1可以添加元素,添加后s1长度变大,容量不变,同时底层数组被修改
s1 = append(s1, 20)
fmt.Printf("[%T]len(s1)=%d,cap(s1)=%d \n",s1,len(s1),cap(s1))
fmt.Println(arr)
// s2如果需要添加元素,因为容量不够,需要进行扩容,开辟新数组,将原来的7,8,9拷贝过来,再添加一个20,长度为4,容量为6
s2 = append(s2,20)
fmt.Printf("[%T]len(s2)=%d,cap(s2)=%d \n",s2,len(s2),cap(s2))
// 此时修改s2的数组,底层数组arr不再受影响
s2[1] = 10
fmt.Println(arr)
// 容量为什么为6?涉及到数组的扩容规则,举个例子如下:
ints := []int{1,2} // 原容量oldCap =2
ints = append(ints,3,4,5) // 预估容量cap = 5
/*
if oldCap * 2 < cap {
newCap = cap
} else {
if oldLen < 1024 {
newCap = oldCap *2
}else if oldLen >= 1024 {
newCap = oldCap *1.25
}
}
*/
// 上面例子中newCap = 5,int数组所占字节为5*8 = 40,但go语言向内存管理模块向操作系统申请的内存容量却没有40大小的,只有48符合,于是newCap = 48/8 = 6
// go语言内存管理模块是16bytes叠加的,8,16,32,48,64,80,96
// 参考博客:https://www.cnblogs.com/ldaniel/p/8502867.html?utm_source=debugrun&utm_medium=referral
fmt.Printf("[%T]len(ints)=%d,cap(ints)=%d \n",ints,len(ints),cap(ints))
// 例子验证第二种情况
ints2 := []int{1,2}
ints2 = append(ints2,3)
// 此时oldCap * 2 > cap ,满足第二种情况,newCap = 4
fmt.Printf("[%T]len(ints2)=%d,cap(ints2)=%d \n",ints2,len(ints2),cap(ints2))
}
打印输出参考
[[]int]len(arr)=10,cap(arr)=10
[[]int]len(s1)=3,cap(s1)=9
[[]int]len(s2)=3,cap(s2)=3
[[]int]len(s1)=4,cap(s1)=9
[0 1 2 3 20 5 6 7 8 9]
[[]int]len(s2)=4,cap(s2)=6
[0 1 2 3 20 5 6 7 8 9]
[[]int]len(ints)=5,cap(ints)=6
[[]int]len(ints2)=3,cap(ints2)=4
Process finished with exit code 0
Go语言中底层数组和切片的关系以及数组扩容规则的更多相关文章
- cpu的控制单元与语言中的控制逻辑有没有关系?
cpu的控制单元与语言中的控制逻辑有没有关系?
- PHP语言中使用JSON和将json还原成数组
从5.2版本开始,PHP原生提供json_encode()和json_decode()函数,前者用于编码,后者用于解码. 一.json_encode() 1 2 3 4 <?php $arr = ...
- 在PHP语言中使用JSON和将json还原成数组
在之前我写过php返回json数据简单实例,刚刚上网,突然发现一篇文章,也是介绍json的,还挺详细,值得参考.内容如下 从5.2版本开始,PHP原生提供json_encode()和json_deco ...
- ***在PHP语言中使用JSON和将json还原成数组(json_decode()的常见错误)
在之前我写过php返回json数据简单实例,刚刚上网,突然发现一篇文章,也是介绍json的,还挺详细,值得参考.内容如下 从5.2版本开始,PHP原生提供json_encode()和json_deco ...
- 转载:在PHP语言中使用JSON和将json还原成数组
一.json_encode() 1 2 3 4 <?php $arr = array ('a'=>1,'b'=>2,'c'=>3,'d'=>4,'e'=>5); e ...
- GO语言总结(3)——数组和切片
上篇博文简单介绍了一下Go语言的基本类型——GO语言总结(2)——基本类型,本篇博文开始介绍Go语言的数组和切片. 一.数组 与其他大多数语言类似,Go语言的数组也是一个元素类型相同的定长的序列. ( ...
- Go语言中的切片(十)
go中数组的长度是固定的,且不同长度的数组是不同类型,这样的限制带来不少局限性.于是切片就来了,切片(Slice)是一个拥有相同类型元素的可变长度的序列.它是基于数组类型做的一层封装.它非常灵活,支持 ...
- C++基础 (8) 第八天 数组指针 模板指针 C语言中的多态 模板函数
1昨日回顾 2 多态的练习-圆的图形 3多态的练习-程序员薪资 4员工管理案例-抽象类和技术员工的实现 employee.h: employee.cpp: technician.h: technici ...
- Go - 数组 和 切片(array、slice)
一.数组 与其他大多数语言类似,Go语言的数组也是一个元素类型相同的定长的序列. (1)数组的创建 数组有 3 种创建方式: 1) [length]Type 2) [length]Type{value ...
随机推荐
- I/O流以及文件的基本操作
文件操作: 文件操作其实就是一个FIle类:我们学习文件操作就是学习File类中的方法: 文件基操: 第一部分:学习文件的基本操作(先扒源码以及文档) Constructor Description ...
- 动态内存:delete作用于空指针
在学习<C++primer 第五版>(中文版)中第12章动态内存与智能指针的时候遇到了一个习题,练习12.13: 练习 12.13:如果执行下面的代码,会发生什么? auto sp=mak ...
- 风变编程(Python自学笔记)第10关-工作量计算器
1.%f的意思是格式化字符串为浮点型,%.1f的意思是格式化字符串为浮点型,并保留1位小数. 2.向上取整:ceil() 使用ceil()方法时需要导入math模块,例如 1 >>> ...
- [Python] 条件 & 循环
条件语句 不加 () 结尾加 : elif else 和 if 成对使用 省略判断条件 String:空字符串为False,其余为True int:0为False,其余为True Bool:True为 ...
- 3.1.5 LTP(Linux Test Project)学习(五)-LTP代码学习
3.1.5 LTP(Linux Test Project)学习(五)-LTP代码学习 Hello小崔 华为技术有限公司 Linux内核开发 2 人赞同了该文章 LTP代码学习方法主要介绍两个步骤, ...
- lambda,filter,map,reduce
# lambda,filter,map,reduce from functools import reduce print('返回一个迭代器') print((x) for x in range(5) ...
- linux中级之keepalived概念
一.HA集群中的相关术语 1.节点(node) 运行HA进程的一个独立主机,称为节点,节点是HA的核心组成部分,每个节点上运行着操作系统和高可用软件服务,在高可用集群中,节点有主次之分,分别称之为主节 ...
- docker仓库登录 配置insecure-registries
1. 配置/etc/docker/daemon.json # cat /etc/docker/daemon.json { "registry-mirrors": ["ht ...
- Mybatis3详解(十四)----Mybatis的分页
1.前言 在前面学习mybatis的时候,会经常对数据进行增删改查操作,使用最多的是对数据库进行查询操作,但是前面都是简单的案例,所以查询的数据量不是很大,自然查询时没有任何压力,但是如果在实际的项目 ...
- Step By Step(Lua面向对象)
Step By Step(Lua面向对象) Lua中的table就是一种对象,但是如果直接使用仍然会存在大量的问题,见如下代码: 1 Account = {balance = 0}2 function ...