为什么Golang创建切片时会有CAPACITY参数

2023-12-08

这是一个非常简单的问题:

If the capacityGolang中的一个切片的容量是可以被超出的,为什么首先要有一个容量参数呢?

我认为这与内存管理,某种“知道在内存中分配切片的位置”,但我不确切知道。


If the capacityGolang中的一个切片的容量是可以被超出的,为什么首先要有一个容量参数呢?

我不知道你的意思,但是不能超过容量。切片可以被索引到其长度(不包括),但不能超过容量,并且可以重新切片到其容量(包括)。

规格:索引表达式:

形式的主要表达a[x]

If a不是地图:...索引x is in range if 0 <= x < len(a),否则就是超出范围

And 规格:切片表达式:

...主要表达式:a[low : high]

对于数组或字符串,索引是in range if 0 <= low <= high <= len(a),否则他们是超出范围。对于切片,索引上界是切片容量cap(a)而不是长度。

并且:

...主要表达式:a[low : high : max]

指数是in range if 0 <= low <= high <= max <= cap(a),否则他们是超出范围.

您可以向内置提供容量make()考虑到未来的增长,因此如果您需要向其附加元素或需要对其进行重新切片,则需要更少的分配。内置的append()如果附加元素有足够的容量,则仅对附加的切片进行重新切片,但如果没有空间容纳新元素,则必须分配一个新的支持数组(并将现有内容复制到其中)。append()将返回新切片,该切片可能指向也可能不指向原始支持数组。

让我们看一个例子。让我们创建一个长度和容量为 0 的切片,并向其添加 10 个元素。为了查看何时发生新的重新分配,我们还打印其第一个元素(第 0 个元素)的地址:

fmt.Println("With 0 capacity")
s := make([]int, 0)
for i := 0; i < 10; i++ {
    s = append(s, i)
    fmt.Println(i, &s[0])
}

这输出:

With 0 capacity
0 0x416030
1 0x416030
2 0x416040
3 0x416040
4 0x452000
5 0x452000
6 0x452000
7 0x452000
8 0x434080
9 0x434080

正如您所看到的,当我们附加第三个(i=2), 第五 (i=4)和第九个元素(i=8),以及当我们附加第一个元素时(因为原始支持数组无法容纳任何元素)。

现在,让我们重复上面的示例,再次创建长度 = 0 但容量 = 10 的初始切片:

fmt.Println("With 10 capacity")
s = make([]int, 0, 10)
for i := 0; i < 10; i++ {
    s = append(s, i)
    fmt.Println(i, &s[0])
}

现在输出将是:

With 10 capacity
0 0x44c030
1 0x44c030
2 0x44c030
3 0x44c030
4 0x44c030
5 0x44c030
6 0x44c030
7 0x44c030
8 0x44c030
9 0x44c030

正如您所看到的,第一个元素的地址从未改变,这意味着后台没有发生新的后备数组分配。

尝试一下上面的例子去游乐场.

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

为什么Golang创建切片时会有CAPACITY参数 的相关文章