Go语言切片

Posted Go程序员开发

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Go语言切片相关的知识,希望对你有一定的参考价值。

Go语言切片

Go语言切片是对数组的抽象。数组的长度不可改变,在特定场景中这样的集合就不太适用,Go中提供了一种灵活,功能强悍的内置类型切片("动态数组"),与数组相比切片的长度是不固定的,可以追加元素,在追加时可能使切片的容量增大。

需要说明,slice 并不是数组或数组指针。它通过内部指针和相关属性引用数组片段,以实现变长方案。

切片定义

第一种,声明一个切片:

var slice []int

切片定义并初始化

var slice0 []int = []int{123}
var slice1 = []int{123}

第二种,通过make来创建切片

var slice0 []int = make([]int10)
var slice1 = make([]int10)
var slice2 = make([]int1010)

第三种,通过 := 语法来定义切片

slice0 := []int{}
slice1 := make([]int10)
slice2 := make([]int1010)

第四种,通过操作数组来创建切片

var array = [...]int{0123456789}
var slice0 []int = array[2:8]

// 可以简写为 var slice []int = array[:end]
var slice1 []int = array[0:6]

// 可以简写为 var slice[]int = array[start:]
var slice2 []int = array[5:10]

// 可以简写为var slice []int = array[:]
var slice3 []int = array[0:len(array)]

// 去掉切片的最后一个元素
var slice4 = array[:len(array)-1]

第五种,通过两个冒号创建切片slice[x:y:z]切片实体[x:y]切片长度len = y-x切片容量cap = z-x

package main

import (
    "fmt"
)

func main() {
    slice := []int{0123456789}
    slice1 := slice[6:8]
    fmt.Printf("slice1 : %v , len : %d , cap : %d\n", slice1, len(slice1), cap(slice1))
    slice2 := slice[2:6:8]
    fmt.Printf("slice2 : %v , len : %d , cap : %d\n", slice2, len(slice2), cap(slice2))
}

slice1[6:8],从第6位到第8位(返回[6 7]),长度len为2,最大可扩充长度cap为4

slice2[2:6:8],从第2位到第6位(返回[2 3 4 5]),长度len为4,最大可扩充长度cap为6

切片操作

切片长度,可以由 len() 函数获取切片长度。
切片容量,可以由 cap() 函数获取切片最长可以达到多少。

package main

import "fmt"

func main() {
    // 通过初始化表达式构造,可使用索引号。
    s1 := []int{01238100}
    fmt.Println(s1, len(s1), cap(s1))

    // 使用 make 创建,指定 len 和 cap 值。
    s2 := make([]int68)
    fmt.Println(s2, len(s2), cap(s2))

    // 省略 cap,相当于 cap = len。
    s3 := make([]int6)
    fmt.Println(s3, len(s3), cap(s3))
}

如果 slice == nil,那么 len、cap 结果都等于 0。

切片追加,使用append() 函数向 slice 尾部添加数据,返回新的 slice

package main

import (
    "fmt"
)

func main() {

    var a = []int{123}

    // 一次 append 一个值
    b := append(a, 4)

    // 一次 append 多个值
    c := append(b, 567)

    // 一次 append 一个切片
    var d = []int{8910}
    e := append(c, d...)

    fmt.Println(a, b, c, d, e)
}

切片拷贝,使用copy() 函数 copy 在两个 slice 间复制数据,复制长度以 len 小的为准。两个 slice 可指向同一底层数组,允许元素区间重叠。

package main

import (
    "fmt"
)

func main() {
    var a = []int{12345}
    b := []int{100200}
    copy(a, b)
    fmt.Println(a, b)
}

运行结果:

 
   
   
 

[100 200 3 4 5] [100 200]

package main

import (
    "fmt"
)

func main() {
    var a = []int{12345}
    b := []int{100200}
    copy(b, a)
    fmt.Println(a, b)
}

运行结果:

[1 2 3 4 5] [1 2]

slice中cap重新分配规律:

package main

import (
    "fmt"
)

func main() {

    s := make([]int01)
    c := cap(s)

    for i := 0; i < 50; i++ {
        s = append(s, i)
        if n := cap(s); n > c {
            fmt.Printf("cap: %d -> %d\n", c, n)
            c = n
        }
    }

}

运行结果:

cap: 1 -> 2
cap: 2 -> 4
cap: 4 -> 8
cap: 8 -> 16
cap: 16 -> 32
cap: 32 -> 64


下一篇:

Go语言容器------敬请期待!

0础学习Go语言系列:


看完本文有收获?那就分享给更多人吧~

长按二维码

以上是关于Go语言切片的主要内容,如果未能解决你的问题,请参考以下文章

go——切片

Go 语言泛型编程之切片

Go 语言范围(Range)

Go 语言范围(Range)

Go 语言入门三部曲:能看懂 Go 语言

Go语言数据结构切片