Golang cap function
last modified May 8, 2025
This tutorial explains how to use the cap built-in function in Go.
We'll cover slice and array capacity with practical examples of capacity usage.
The cap function returns the capacity of a slice or array in Go. Capacity represents the maximum number of elements the underlying array can hold. For arrays, capacity is always equal to length.
In Go, cap is primarily used with slices to understand their growth
potential. Knowing a slice's capacity helps optimize memory usage and performance.
Basic array capacity example
For arrays, cap always returns the same value as len.
This example demonstrates capacity with a fixed-size array.
Note: Arrays have fixed capacity determined at declaration.
package main
import "fmt"
func main() {
arr := [5]int{1, 2, 3, 4, 5}
fmt.Println("Array:", arr)
fmt.Println("Length:", len(arr))
fmt.Println("Capacity:", cap(arr)) // Same as length for arrays
}
The array has fixed size 5, so both length and capacity are 5. Capacity cannot change for arrays after declaration.
Slice capacity basics
Slices can grow up to their capacity before needing reallocation. This example shows how slice capacity differs from length.
package main
import "fmt"
func main() {
s := make([]int, 3, 5) // length 3, capacity 5
fmt.Println("Slice:", s)
fmt.Println("Length:", len(s))
fmt.Println("Capacity:", cap(s))
s = append(s, 4)
fmt.Println("\nAfter append:")
fmt.Println("Length:", len(s))
fmt.Println("Capacity:", cap(s)) // Still 5
}
The slice starts with length 3 but capacity 5. After appending one element, length becomes 4 while capacity remains 5.
Capacity growth with append
When a slice exceeds its capacity, Go automatically allocates a new larger array. This example demonstrates capacity growth during append operations.
package main
import "fmt"
func main() {
s := make([]int, 0, 2) // length 0, capacity 2
fmt.Printf("Initial cap: %d\n", cap(s))
s = append(s, 1)
s = append(s, 2)
fmt.Printf("After 2 appends cap: %d\n", cap(s))
s = append(s, 3) // Exceeds capacity
fmt.Printf("After 3rd append cap: %d\n", cap(s)) // Capacity doubles
}
When exceeding initial capacity, Go typically doubles the capacity. This growth pattern helps amortize allocation costs over multiple append operations.
Capacity of slice expressions
Slice operations affect capacity differently. This example shows how slicing impacts capacity calculations.
package main
import "fmt"
func main() {
original := make([]int, 5, 10) // length 5, capacity 10
// Full slice
fmt.Printf("Original cap: %d\n", cap(original))
// Slice from index 2
slice1 := original[2:]
fmt.Printf("Slice from 2 cap: %d\n", cap(slice1)) // 8 (10-2)
// Slice from index 2 to 4
slice2 := original[2:4]
fmt.Printf("Slice 2:4 cap: %d\n", cap(slice2)) // Still 8
}
Slicing affects capacity based on the starting index. The capacity becomes the original capacity minus the starting index of the slice.
Practical capacity usage
Understanding capacity helps optimize slice operations. This example shows pre-allocation using capacity for performance.
package main
import (
"fmt"
"time"
)
func processWithoutPreallocation(n int) {
start := time.Now()
var s []int
for i := 0; i < n; i++ {
s = append(s, i)
}
elapsed := time.Since(start)
fmt.Printf("Without preallocation: %v\n", elapsed)
}
func processWithPreallocation(n int) {
start := time.Now()
s := make([]int, 0, n) // Preallocate capacity
for i := 0; i < n; i++ {
s = append(s, i)
}
elapsed := time.Since(start)
fmt.Printf("With preallocation: %v\n", elapsed)
}
func main() {
const size = 1000000
processWithoutPreallocation(size)
processWithPreallocation(size)
}
Preallocating capacity avoids repeated allocations during append operations. This significantly improves performance for large slices.
Source
This tutorial covered the cap function in Go with practical
examples of capacity usage with arrays and slices.
Author
List all Golang tutorials.