Go语言 数组、切片、map的区别

简介: Go语言 数组、切片、map的区别

本篇只进行比较!


类型比较


数组:值类型

切片:引用类型

map:引用类型


语法比较


数组的语法:var name [5]string []必须指定长度数字

var a  [10]int //声明数组

切片的语法:var name []string

var b []int    //声明切片

map的语法:var map变量名 map[key类型]vlaue类型 []中必须指定类型

var c map[string]int   //声明map类型


长度和容量规则


数组:固定长度,无容量。数组的长度在声明时就要给出

切片:动态长度,有容量,容量可以理解成可达到的最大长度

切片可以由数组构造来,不改变长度的情况下,共享内存,即切片的第一个元素发生变化,数组的第一个元素也将发生变化。

package main
import "fmt"
func main() {
  a := [10]int{1,2,3,4,5}
  b := a[:]  //声明切片b由数组a构造
  b[4] =6 //只修改了切片b的第四个元素,数组a也将发生改变
  fmt.Println(a)
  fmt.Println(b)
}

输出结果:

[1 2 3 4 6 0 0 0 0 0]
[1 2 3 4 6 0 0 0 0 0]

上面不发生变化的只发生再数组转换成切片的情况下,如果数组与数组之间的赋值,是不会共享内存的

package main
import "fmt"
func main() {
  a := [...]string{"USA", "China", "India", "Germany", "France"}
  b := a // a的一个副本被分配给b
  b[0] = "Singapore"
  fmt.Println("a is ", a)
  fmt.Println("b is ", b)
  fmt.Printf("%T%T",a,b)
}

输出结果:

a is  [USA China India Germany France]
b is  [Singapore China India Germany France]
[5]string[5]string //都是数组类型,同类型

切片的长度可使用append参数,改变后的切片超出容量将不共享内存

package main
import "fmt"
func main() {
  a := [...]int{1,2,3,4,5} //a数组
  b := []int{6,7,8,9,10}   //b切片
  c := a[:]               //声明切片b由数组a构造
  c = append(c,b...) //必须是切片类型才能追加,并第二个切片加“...”
  fmt.Println(a)
  fmt.Println(b)
  fmt.Println(c)
}

输出结果:

[1 2 3 4 5]
[6 7 8 9 10]
[1 2 3 4 5 6 7 8 9 10]

map:动态长度

map是无序的,我们无法决定它的返回顺序,这是因为 Map 是使用 hash 表来实现的。


声明比较


package main
import "fmt"
func main() {
  var a  [10]int //声明数组
  var b []int    //声明切片
  var c map[string]int   //声明map类型
  fmt.Println(a)
  fmt.Println(b == nil)
  fmt.Println(c == nil)
}

输出结果:

[0 0 0 0 0 0 0 0 0 0]
true
true

数组是不能被判断是否是nil,因为数组必须在声明时申请内存

切片和map可以被判断是否是nil


初始化比较


切片和map是可以被make初始化的,数组不行,数组必须在声明时初始化。

初始化之后才能有内存地址

package main
import "fmt"
func main() {
  a := make([]int,5,10)
  b := make(map[string]int,10)
  fmt.Printf("%T\n",a)
  fmt.Printf("%T",b)
}

输出结果:

[]int
map[string]int

另外,new和make都是用于初始化的,它们两个区别在于new只能初始化值类型(int、string等),make只能初始化引用类型(切片、map、channel)


相互转换


数组可以转换成切片

package main
import "fmt"
func main() {
  var a  [10]int
  var b  = a[:] //不加[:]代表转化成数组
  fmt.Println(a)
  fmt.Println(b)
}

输出结果:

[0 0 0 0 0 0 0 0 0 0]
[0 0 0 0 0 0 0 0 0 0]


修改值的区别

package main
import "fmt"
func main() {
  a := make([]int,5,10)
  b := make(map[string]int,10)
  c := [5]int{}
  c[1]=10 //把数组c第一个元素修改成10
  a[1] = 10 //把切片a第一个元素修改成10
  b["Go语言"] = 1 // 把键值对存入到map中
  b["Go语言"] = 2  //把key是Go语言的vlaue修改成2
  fmt.Printf("a的类型:%T,a的值:%v\n",a,a)
  fmt.Printf("b的类型:%T,b的值:%v\n",b,b)
  fmt.Printf("c的类型:%T,c的值:%v\n",c,c)
}

输出结果:

a的类型:[]int,a的值:[0 10 0 0 0]
b的类型:map[string]int,b的值:map[Go语言:2]
c的类型:[5]int,c的值:[0 10 0 0 0]


遍历比较

package main
import "fmt"
func main() {
  a := make([]int,3,10)
  b := make(map[string]int,10)
  c := [3]int{}
  a[0] =99
  b["Go语言"]= 99
  c[0] =99
  for k,v :=range c{
    fmt.Println(k,v)
  }
  for k,v :=range b {
    fmt.Println(k,v)
  }
  for k,v :=range a {
    fmt.Println(k,v)
  }
}

都可以使用for-range遍历

相关文章
|
3天前
|
测试技术 Go API
Go 切片导致 rand.Shuffle 产生重复数据的原因与解决方案
在 Go 语言开发中,使用切片时由于其底层数据共享特性,可能会引发意想不到的 Bug。本文分析了 `rand.Shuffle` 后切片数据重复的问题,指出原因在于切片是引用类型,直接赋值会导致底层数组共享,进而影响原始数据。解决方案是使用 `append` 进行数据拷贝,确保独立副本,避免 `rand.Shuffle` 影响原始数据。总结强调了切片作为引用类型的特性及正确处理方法,确保代码稳定性和正确性。
103 81
|
7天前
|
监控 Linux PHP
【02】客户端服务端C语言-go语言-web端PHP语言整合内容发布-优雅草网络设备监控系统-2月12日优雅草简化Centos stream8安装zabbix7教程-本搭建教程非docker搭建教程-优雅草solution
【02】客户端服务端C语言-go语言-web端PHP语言整合内容发布-优雅草网络设备监控系统-2月12日优雅草简化Centos stream8安装zabbix7教程-本搭建教程非docker搭建教程-优雅草solution
57 20
|
5天前
|
存储 监控 算法
探秘员工泄密行为防线:基于Go语言的布隆过滤器算法解析
在信息爆炸时代,员工泄密行为对企业构成重大威胁。本文聚焦布隆过滤器(Bloom Filter)这一高效数据结构,结合Go语言实现算法,帮助企业识别和预防泄密风险。通过构建正常操作“指纹库”,实时监测员工操作,快速筛查可疑行为。示例代码展示了如何利用布隆过滤器检测异常操作,并提出优化建议,如调整参数、结合日志分析系统等,全方位筑牢企业信息安全防线,守护核心竞争力。
|
13天前
|
Go C语言
Go语言入门:分支结构
本文介绍了Go语言中的条件语句,包括`if...else`、`if...else if`和`switch`结构,并通过多个练习详细解释了它们的用法。`if...else`用于简单的条件判断;`if...else if`处理多条件分支;`switch`则适用于基于不同值的选择逻辑。特别地,文章还介绍了`fallthrough`关键字,用于优化重复代码。通过实例如判断年龄、奇偶数、公交乘车及成绩等级等,帮助读者更好地理解和应用这些结构。
35 14
|
27天前
|
存储 监控 算法
内网监控系统之 Go 语言布隆过滤器算法深度剖析
在数字化时代,内网监控系统对企业和组织的信息安全至关重要。布隆过滤器(Bloom Filter)作为一种高效的数据结构,能够快速判断元素是否存在于集合中,适用于内网监控中的恶意IP和违规域名筛选。本文介绍其原理、优势及Go语言实现,提升系统性能与响应速度,保障信息安全。
30 5
|
1月前
|
存储 安全 Go
Go语言中的map数据结构是如何实现的?
Go 语言中的 `map` 是基于哈希表实现的键值对数据结构,支持快速查找、插入和删除操作。其原理涉及哈希函数、桶(Bucket)、动态扩容和哈希冲突处理等关键机制,平均时间复杂度为 O(1)。为了确保线程安全,Go 提供了 `sync.Map` 类型,通过分段锁实现并发访问的安全性。示例代码展示了如何使用自定义结构体和切片模拟 `map` 功能,以及如何使用 `sync.Map` 进行线程安全的操作。
|
12天前
|
监控 关系型数据库 MySQL
【01】客户端服务端C语言-go语言-web端PHP语言整合内容发布-优雅草网络设备监控系统-硬件设备实时监控系统运营版发布-本产品基于企业级开源项目Zabbix深度二开-分步骤实现预计10篇合集-自营版
【01】客户端服务端C语言-go语言-web端PHP语言整合内容发布-优雅草网络设备监控系统-硬件设备实时监控系统运营版发布-本产品基于企业级开源项目Zabbix深度二开-分步骤实现预计10篇合集-自营版
22 0
|
2月前
|
存储 Go 索引
go语言中数组和切片
go语言中数组和切片
51 7
|
8月前
|
Go
go语言数组与切片
go语言数组与切片
|
5月前
|
编译器 Go 索引
Go数组、多维数组和切片(动态数组),及常用函数len(),cap(),copy(),append()在切片中的使用
本文介绍了Go语言中数组、多维数组和切片(动态数组)的基本概念和操作,包括数组的定义、初始化、访问,多维数组的定义和访问,以及切片的创建、使用和扩容。同时,还讲解了切片中常用的函数len()、cap()、copy()和append()的使用方法。