Deprecated: imwpcache\f884414bce24ee67f\f73723ec7b1919fa5::__construct(): Implicitly marking parameter $YECBGYFECGEAFWHA as nullable is deprecated, the explicit nullable type must be used instead in /www/wwwroot/www.chuangxiangniao.com/wp-content/plugins/imwpcache-dist/build/f884414bce24ee67ff73723ec7b1919fa5.php on line 2

Deprecated: imwpcache\f884414bce24ee67f\f73723ec7b1919fa5::__construct(): Implicitly marking parameter $BBWFDDBHHYHDXXAB as nullable is deprecated, the explicit nullable type must be used instead in /www/wwwroot/www.chuangxiangniao.com/wp-content/plugins/imwpcache-dist/build/f884414bce24ee67ff73723ec7b1919fa5.php on line 2
Go语言中数组与切片的深度解析与实践_创想鸟

Go语言中数组与切片的深度解析与实践

go语言中数组与切片的深度解析与实践

本文旨在深入探讨Go语言中数组(Array)和切片(Slice)这两种核心数据类型的本质区别与使用场景。我们将澄清常见的混淆点,特别是关于它们在函数参数传递时的行为差异,并通过实际代码示例,详细解释为何切片在传递给如sort.Ints等函数后能修改其底层数据,而数组则不能。理解这些概念对于编写高效、正确的Go程序至关重要。

Go语言中的数组:固定与值语义

在Go语言中,数组是一种具有固定长度的同类型元素序列。数组的长度是其类型的一部分,这意味着[10]int和[20]int是两种完全不同的类型。

核心特性:

固定长度: 一旦声明,数组的长度就不能改变。值类型: 数组是值类型。当一个数组被赋值给另一个数组,或者作为函数参数传递时,Go会复制整个数组的所有元素。这意味着函数接收的是数组的一个副本,对副本的修改不会影响原始数组。

数组声明与传值示例:

package mainimport "fmt"func modifyArray(arr [5]int) {    arr[0] = 99 // 修改的是副本    fmt.Println("在函数内部修改后的数组副本:", arr)}func main() {    var arrValue = [5]int{1, 2, 3, 4, 5}    fmt.Println("原始数组:", arrValue)    modifyArray(arrValue) // 传递的是arrValue的副本    fmt.Println("函数调用后原始数组:", arrValue) // 原始数组未被修改}

输出:

立即学习“go语言免费学习笔记(深入)”;

原始数组: [1 2 3 4 5]在函数内部修改后的数组副本: [99 2 3 4 5]函数调用后原始数组: [1 2 3 4 5]

从示例中可以看出,modifyArray函数内部对数组的修改并未影响到main函数中的原始数组,这充分体现了数组的值类型特性和按值传递的语义。

Go语言中的切片:动态与引用语义

与数组不同,切片提供了一种更强大、更灵活的数据结构,它代表了一个底层数组的连续片段。切片本身不存储任何数据,它只是对底层数组的一个“视图”。

核心特性:

动态长度: 切片的长度是可变的,可以在运行时进行扩展(通过append操作,可能导致底层数组的重新分配)。引用类型(或称“切片头是值类型,但指向引用数据”): 切片在内部由三个部分组成:指向底层数组的指针(ptr)、切片的长度(len)和切片的容量(cap)。当切片作为函数参数传递时,Go会复制这个切片头(即ptr、len、cap这三个值)。虽然切片头被复制了,但复制后的切片头仍然指向与原始切片相同的底层数组。因此,通过复制后的切片头对底层数组元素的修改,会反映在原始切片上。

切片声明与传值示例:

在Go语言中,使用字面量[]int{1, 5, 2, 3, 7}声明的变量,它是一个切片(Slice),而不是数组。切片字面量的声明方式与数组字面量相似,但省略了元素计数。

package mainimport "fmt"func modifySlice(s []int) {    s[0] = 99 // 修改的是底层数组的元素    fmt.Println("在函数内部修改后的切片:", s)}func main() {    var sliceValue = []int{1, 2, 3, 4, 5} // 这是一个切片    fmt.Println("原始切片:", sliceValue)    modifySlice(sliceValue) // 传递的是切片头的副本    fmt.Println("函数调用后原始切片:", sliceValue) // 原始切片被修改}

输出:

立即学习“go语言免费学习笔记(深入)”;

原始切片: [1 2 3 4 5]在函数内部修改后的切片: [99 2 3 4 5]函数调用后原始切片: [99 2 3 4 5]

从示例中可以看出,modifySlice函数内部对切片元素的修改,确实影响到了main函数中的原始切片。这是因为虽然切片头被复制了,但两个切片头都指向同一个底层数组,所以对底层数组的修改是共享的。

深入理解 sort.Ints 的行为

现在我们来解释最初的困惑:为什么sort.Ints(arrayValue)能修改变量,即使它看起来像一个数组。

根据Go标准库的定义,sort.Ints函数的签名如下:

func Ints(a []int)

它明确要求传入一个[]int类型的参数,即一个整型切片。

分析用户代码:

var av = []int{1,5,2,3,7} // 这行代码声明的是一个切片,不是数组!fmt.Println(av)sort.Ints(av) // 传入的是切片fmt.Println(av)

当av被声明为[]int{1,5,2,3,7}时,它实际上创建了一个切片。因此,将其传递给sort.Ints是完全合法的。sort.Ints函数接收到的是av切片头的一个副本,这个副本指向与av相同的底层数组。sort.Ints通过这个切片头访问并修改底层数组的元素,从而实现了对切片内容的排序。由于原始切片av和函数内部的切片都指向同一个底层数组,所以排序操作会直接反映在av上。

如果尝试将数组传递给 sort.Ints:

如果声明一个真正的数组并尝试传递给sort.Ints,Go编译器会报错,因为类型不匹配。

package mainimport (    "fmt"    "sort")func main() {    var arrValue = [5]int{1, 5, 2, 3, 7} // 这是一个数组    fmt.Println("原始数组:", arrValue)    // sort.Ints(arrValue) // 编译错误: cannot use arrValue (type [5]int) as type []int in argument to sort.Ints    // 如果要排序数组,需要先将其转换为切片    sort.Ints(arrValue[:]) // 通过切片表达式将数组转换为切片    fmt.Println("排序后数组(通过切片视图修改):", arrValue)}

输出:

立即学习“go语言免费学习笔记(深入)”;

原始数组: [1 5 2 3 7]排序后数组(通过切片视图修改): [1 2 3 5 7]

通过arrValue[:],我们创建了一个指向arrValue底层数组的完整切片视图,然后将这个切片视图传递给sort.Ints。这样,sort.Ints就能修改底层数组,从而实现对原始数组的排序。

数组与切片的核心区别总结

特性 数组 (Array) 切片 (Slice)

长度固定长度,声明后不可改变动态长度,可在运行时增长或缩短类型长度是类型的一部分,如[5]int和[10]int是不同类型长度不是类型的一部分,[]int表示所有整型切片内存值类型,直接存储元素引用类型,内部包含指针、长度和容量,指向底层数组传参按值传递,复制整个数组复制切片头(指针、长度、容量),指向同一底层数组用途较少直接使用,常作为切片的底层存储Go中最常用的动态序列数据结构,功能强大

实践建议

优先使用切片: 在Go语言中,除非你确实需要一个固定大小的集合且不希望其大小改变,否则几乎总是应该使用切片。切片提供了更灵活、更Go-idiomatic的方式来处理序列数据。理解切片扩容: 当切片容量不足时,append操作可能会导致底层数组的重新分配,这会影响性能。在处理大量数据时,预估并设置合适的初始容量(使用make([]T, length, capacity))可以优化性能。警惕切片共享底层数组: 当从一个现有切片创建新切片(如slice[low:high])时,新切片会与原切片共享同一个底层数组。对其中一个切片的修改可能会影响另一个。如果需要完全独立的数据副本,请使用copy函数。

总结

Go语言的数组和切片是两种截然不同的数据类型,尽管它们在语法上有些相似。数组是固定长度的值类型,按值传递时会进行完整复制;而切片是动态长度的引用类型(其头信息是值类型,但指向引用数据),按值传递时只复制切片头,因此可以修改其共享的底层数组。理解这些核心差异对于避免常见错误、编写高效且易于维护的Go代码至关重要。始终记住,[]int{…}是切片,而非数组。

以上就是Go语言中数组与切片的深度解析与实践的详细内容,更多请关注创想鸟其它相关文章!

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。
如发现本站有涉嫌抄袭侵权/违法违规的内容, 请发送邮件至 chuangxiangniao@163.com 举报,一经查实,本站将立刻删除。
发布者:程序猿,转转请注明出处:https://www.chuangxiangniao.com/p/1405470.html

赞 (0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
Go语言中的匿名函数:实现与应用类似Lambda表达式的功能
上一篇 2025年12月15日 21:24:46
Golang的Go调度器(scheduler)是如何管理和调度goroutine的
下一篇 2025年12月15日 21:24:58

相关推荐

  • 怎么用豆包AI帮我转换编程语言 3分钟学会用AI实现代码语言自动转换

    怎么用豆包AI帮我转换编程语言 3分钟学会用AI实现代码语言自动转换怎么用豆包AI帮我转换编程语言 3分钟学会用AI实现代码语言自动转换怎么用豆包AI帮我转换编程语言 3分钟学会用AI实现代码语言自动转换怎么用豆包AI帮我转换编程语言 3分钟学会用AI实现代码语言自动转换

    豆包ai实现代码语言自动转换的方法如下:1. 准备好原始代码并明确标注目标语言,确保代码无语法错误且功能清晰;2. 使用豆包ai的对话功能进行提问,粘贴代码并准确描述转换需求,避免模糊指令;3. 检查转换后的代码是否可用,通过通读、运行测试用例及对比行为差异进行验证,如有问题可继续向ai反馈修改。 …

    2026年9月27日 • 用户投稿
    000
  • 猫眼如何举报不当评论内容_猫眼不当评论举报处理流程

    猫眼如何举报不当评论内容_猫眼不当评论举报处理流程猫眼如何举报不当评论内容_猫眼不当评论举报处理流程猫眼如何举报不当评论内容_猫眼不当评论举报处理流程猫眼如何举报不当评论内容_猫眼不当评论举报处理流程

    发现不当评论可举报,通过猫眼App内功能直接投诉,选择举报原因并提交;若无效可联系客服人工申诉并提供证据;也可通过官网提交反馈,上传截图与说明。 如果您在猫眼平台发现不当评论内容,可能会影响其他用户的观影决策或包含违规信息,可以通过以下流程进行举报。举报成功后,平台将根据规则对内容进行审核与处理。 …

    2026年9月27日 • 用户投稿
    100
  • 外网博主对《失落之魂》十分看好:有望竞争年度最佳

    外网博主对《失落之魂》十分看好:有望竞争年度最佳外网博主对《失落之魂》十分看好:有望竞争年度最佳外网博主对《失落之魂》十分看好:有望竞争年度最佳外网博主对《失落之魂》十分看好:有望竞争年度最佳

    由国内独立开发者杨冰领衔打造、备受瞩目的动作游戏《失落之魂》(Lost Soul Aside)即将在本月底正式发售,引发全球玩家高度关注。 近日,海外知名游戏实况主Dannozdirect Gaming发布了一段深度解析视频,对这款自2016年启动开发的作品给予了极高评价,甚至认为它具备角逐“年度最…

    2026年9月27日 • 用户投稿
    000
  • 详解抖音平台订单导出的具体步骤

    详解抖音平台订单导出的具体步骤详解抖音平台订单导出的具体步骤详解抖音平台订单导出的具体步骤详解抖音平台订单导出的具体步骤

    随着电商行业的不断壮大,抖音已逐渐成为众多电商从业者不可或缺的运营阵地。在日常经营中,订单导出是一项极为关键的操作,能够帮助商家高效整理交易数据,优化发货流程,并提升客户服务体验。本文将从多个方面深入介绍如何在抖音平台完成订单导出操作。 1. 登录抖音商家后台 首先需进入抖音商家后台系统。打开抖音A…

    2026年9月27日 • 用户投稿
    000
  • sublime怎么连接ssh_Sublime通过SFTP插件连接远程服务器教程

    sublime怎么连接ssh_Sublime通过SFTP插件连接远程服务器教程sublime怎么连接ssh_Sublime通过SFTP插件连接远程服务器教程sublime怎么连接ssh_Sublime通过SFTP插件连接远程服务器教程sublime怎么连接ssh_Sublime通过SFTP插件连接远程服务器教程

    首先安装SFTP插件,通过Package Control搜索并安装;然后在项目中右键选择SFTP → Setup Server生成配置文件;接着编辑sftp-config.json,填写服务器IP、用户名、密码、端口、远程路径和本地路径等信息;推荐使用SSH密钥登录,可配置ssh_key_file路…

    2026年9月27日 • 用户投稿
    200
  • Logback:阻止日志输出到控制台,仅保留文件输出

    Logback:阻止日志输出到控制台,仅保留文件输出Logback:阻止日志输出到控制台,仅保留文件输出Logback:阻止日志输出到控制台,仅保留文件输出Logback:阻止日志输出到控制台,仅保留文件输出

    本文档旨在解决Logback在未配置ConsoleAppender的情况下,仍然将日志输出到控制台的问题。通过设置logger的additivity属性为false,可以有效地阻止日志信息继续向上级logger传递,从而实现仅将日志写入文件的目的,避免在控制台产生冗余信息。本文将详细介绍该解决方案,…

    2026年9月27日 • 用户投稿
    100
  • ChatGPT怎么上传PDF 文档阅读与分析功能详解

    ChatGPT怎么上传PDF 文档阅读与分析功能详解ChatGPT怎么上传PDF 文档阅读与分析功能详解ChatGPT怎么上传PDF 文档阅读与分析功能详解ChatGPT怎么上传PDF 文档阅读与分析功能详解

    chatgpt 可以通过多种方式“看到”pdf内容并进行分析。1. chatgpt plus或企业版用户可直接上传pdf文件,系统自动解析后可用于提取信息、总结报告、回答问题或翻译文本;2. 普通用户可手动复制粘贴pdf中的文字内容到对话框中,适用于小段内容处理;3. 使用第三方工具如smallpd…

    2026年9月27日 • 用户投稿
    100
  • 《新VR战士》确定不采用客串角色 将强化剧情叙事

    《新VR战士》确定不采用客串角色 将强化剧情叙事《新VR战士》确定不采用客串角色 将强化剧情叙事《新VR战士》确定不采用客串角色 将强化剧情叙事《新VR战士》确定不采用客串角色 将强化剧情叙事

    近日,世嘉公开了《VR战士》系列新作的最新动态,明确表示这款正在开发中的格斗游戏将不会加入来自其他IP的跨界角色。在与Giant Bomb的访谈中,制作人山田精一强调,团队的核心目标是打造一个独立且完整的《VR战士》世界观,同时融入新颖设计以吸引新玩家并回馈长期支持的老粉丝。 谈及为何在系列沉寂多年…

    2026年9月27日 • 用户投稿
    100
  • Safari浏览器无痕模式怎么开启_Safari浏览器隐私浏览模式开启方式

    Safari浏览器无痕模式怎么开启_Safari浏览器隐私浏览模式开启方式Safari浏览器无痕模式怎么开启_Safari浏览器隐私浏览模式开启方式Safari浏览器无痕模式怎么开启_Safari浏览器隐私浏览模式开启方式Safari浏览器无痕模式怎么开启_Safari浏览器隐私浏览模式开启方式

    首先在Safari中点击标签页图标,再点右上角箭头选择“无痕浏览”即可开启;完成浏览后,点击左上角“常规”按钮可切回普通模式;iPad用户还可长按Safari图标,从快捷菜单选择“新无痕浏览窗口”直接启动。 如果您希望在浏览网页时防止Safari保存历史记录、搜索记录或表单数据,可以启用无痕模式来保…

    2026年9月27日 • 用户投稿
    000
  • 剪映 AI 一键成片?素材筛选与节奏把控实用技巧

    剪映 AI 一键成片?素材筛选与节奏把控实用技巧剪映 AI 一键成片?素材筛选与节奏把控实用技巧剪映 AI 一键成片?素材筛选与节奏把控实用技巧剪映 AI 一键成片?素材筛选与节奏把控实用技巧

    要做出高质量视频,素材筛选和节奏把控是关键。首先,选择内容相关、能表达情绪且多样化的素材,并确保技术指标合格;其次,根据视频基调灵活运用快切或慢放,合理使用转场与音乐,适当留白;最后,可借助剪映ai辅助筛选高光时刻并调整节奏,但需人工复核。 ☞☞☞AI 智能聊天, 问答助手, AI 智能搜索, 免费…

    2026年9月27日 • 用户投稿
    000
  • 古生物复活计划:豆包AI+PaleoAI还原恐龙生态图文报告

    古生物复活计划:豆包AI+PaleoAI还原恐龙生态图文报告古生物复活计划:豆包AI+PaleoAI还原恐龙生态图文报告古生物复活计划:豆包AI+PaleoAI还原恐龙生态图文报告古生物复活计划:豆包AI+PaleoAI还原恐龙生态图文报告

    古生物复活计划并非复活恐龙,而是利用ai还原远古生态环境,并以图文形式呈现。paleoai负责搜集整理古生物学数据,包括化石、地质和植物信息;豆包ai则通过深度学习分析数据,推断气候、植被和动物行为,并生成3d生态场景。两者分工明确:paleoai确保数据科学性,豆包ai实现可视化呈现。为确保准确性…

    2026年9月27日 • 用户投稿
    200
  • 华为WATCH GT 6系列正式发布:超长续航全能智能手表亮相

    华为WATCH GT 6系列正式发布:超长续航全能智能手表亮相华为WATCH GT 6系列正式发布:超长续航全能智能手表亮相华为WATCH GT 6系列正式发布:超长续航全能智能手表亮相华为WATCH GT 6系列正式发布:超长续航全能智能手表亮相

    2025年9月24日,华为watch gt 6系列在线上举行的华为穿戴音频新品发布会正式亮相,再次彰显华为在高端智能手表市场的强劲竞争力。 自2018年首代产品问世以来,GT系列始终聚焦长续航、健康监测与运动进阶功能,持续引领智能穿戴创新方向。市场研究机构IDC最新数据显示,2025年第二季度,华为…

    2026年9月27日 • 用户投稿
    200
  • 详解:如何将抖音订单接口接入到小程序上

    详解:如何将抖音订单接口接入到小程序上详解:如何将抖音订单接口接入到小程序上详解:如何将抖音订单接口接入到小程序上详解:如何将抖音订单接口接入到小程序上

    前言 作为全球领先的短视频平台,抖音拥有庞大的用户群体和活跃的电商生态。与此同时,小程序凭借其轻便、即用即走的特性,成为移动应用的重要形态之一。本文将深入讲解如何将抖音的订单接口成功接入小程序,助力开发者融合两大平台优势,提升服务体验与商业转化能力。 步骤一:理解抖音订单接口与小程序基础 在实际接入…

    2026年9月27日 • 用户投稿
    100
  • 360极速浏览器怎么把网页保存为图片_360极速浏览器网页长截图与另存为图片功能

    360极速浏览器怎么把网页保存为图片_360极速浏览器网页长截图与另存为图片功能360极速浏览器怎么把网页保存为图片_360极速浏览器网页长截图与另存为图片功能360极速浏览器怎么把网页保存为图片_360极速浏览器网页长截图与另存为图片功能360极速浏览器怎么把网页保存为图片_360极速浏览器网页长截图与另存为图片功能

    首先使用360极速浏览器内置长截图功能,点击菜单中“网页截图”选择“长截图”自动捕获全页并保存为PNG;其次可右键查看是否有“将页面另存为图片”选项直接导出JPEG或PNG格式;最后当功能受限时,通过扩展中心安装“FireShot”等插件实现高清全页截图并下载。 如果您希望将浏览的网页完整保存为图片…

    2026年9月27日 • 用户投稿
    100
  • 抖音店铺订单信息加密解密技巧

    抖音店铺订单信息加密解密技巧抖音店铺订单信息加密解密技巧抖音店铺订单信息加密解密技巧抖音店铺订单信息加密解密技巧

    随着电商行业的迅猛发展,越来越多的商家入驻抖音平台开设线上店铺。然而,在处理订单数据时,由于抖音平台对订单信息进行了加密保护,不少商家在获取和解析订单内容时面临挑战。本文将从多个维度深入解析抖音店铺订单信息的加密与解密方法,助力商家高效处理订单数据,提升整体运营效率。 抖音店铺订单信息的加密机制 抖…

    2026年9月27日 • 用户投稿
    100
  • 使用 GSON 和 Kotlin 泛型将 JSON 转换为自定义类

    使用 GSON 和 Kotlin 泛型将 JSON 转换为自定义类使用 GSON 和 Kotlin 泛型将 JSON 转换为自定义类使用 GSON 和 Kotlin 泛型将 JSON 转换为自定义类使用 GSON 和 Kotlin 泛型将 JSON 转换为自定义类

    本文档旨在解决在使用 GSON 和 Kotlin 泛型进行 JSON 反序列化时,将 JSON 数据转换为自定义类时遇到的 ClassCastException 问题。通过分析问题原因,提供解决方案,并介绍未来 GSON 版本中对此类问题的改进,帮助开发者更好地理解和使用 GSON 进行 Kotli…

    2026年9月27日 • 用户投稿
    100
  • 国内AI工具权威排名 十大国产人工智能应用解析

    国内AI工具权威排名 十大国产人工智能应用解析国内AI工具权威排名 十大国产人工智能应用解析国内AI工具权威排名 十大国产人工智能应用解析国内AI工具权威排名 十大国产人工智能应用解析

    要选择适合自己的国产ai工具,首先需明确需求,再根据易用性、功能性、性价比、社区支持和数据安全等五个方面进行评估。图像处理方面,推荐“稿定设计”和百度ai开放平台api;自然语言处理方面,有“秘塔写作猫”、百度翻译和有道翻译等;代码生成方面,阿里云的“通义灵码”具有较大潜力。国内ai工具发展迅速,应…

    2026年9月27日 • 用户投稿
    500
  • 解决Kotlin中Gson与Reified泛型结合时的类型转换异常

    解决Kotlin中Gson与Reified泛型结合时的类型转换异常解决Kotlin中Gson与Reified泛型结合时的类型转换异常解决Kotlin中Gson与Reified泛型结合时的类型转换异常解决Kotlin中Gson与Reified泛型结合时的类型转换异常

    在kotlin开发中,结合gson库处理泛型数据反序列化是常见的场景。kotlin的reified泛型特性为我们提供了在运行时访问泛型类型信息的能力,这在与java互操作(如使用gson)时显得尤为重要。然而,如果未能正确理解和应用reified,便可能遭遇java.lang.classcastex…

    2026年9月27日 • 用户投稿
    100
  • 为什么内存频率存在基础频率和超频频率?开启XMP/EXPO算超频吗?

    内存基础频率遵循JEDEC标准,确保兼容性与稳定性,如DDR5-4800;超频频率通过XMP/EXPO技术提升性能,需主板支持并手动开启,属于安全范围内的性能释放。 内存存在基础频率和超频频率,主要是为了在兼容性与性能之间取得平衡。开启XMP/EXPO通常被认为是超频的一种形式。 基础频率确保广泛兼…

    2026年9月27日
    400
  • CPU硅脂与钎焊散热工艺的性能差距有多大?

    钎焊导热远优于硅脂,因金属键合大幅降低界面热阻,使CPU温度更低、性能释放更强、超频潜力更大,尤其在高负载下优势明显。 CPU硅脂与钎焊散热工艺之间的性能差距,在我看来,通常能达到数度到十余度甚至更高的温差,这在高性能计算场景下,足以显著影响CPU的性能释放和稳定性。简单来说,钎焊在导热效率上有着硅…

    2026年9月27日
    100

发表回复

登录后才能评论
关注微信