Skip to content

Slices in Go

New Course Coming Soon:

Get Really Good at Git

A slice is a data structure similar to an array, but it can change in size.

Under the hood, slices use an array and they are an abstraction built on top of them that makes them more flexible and useful (think about arrays as lower level).

You will use slices in a way that’s very similar to how you use arrays in higher level languages.

You define a slice similarly to an array, omitting the length:

var mySlice []string //a slice of strings

You can initialize the slice with values:

var mySlice = []string{"First", "Second", "Third"}

//or

mySlice := []string{"First", "Second", "Third"}

You can create an empty slice of a specific length using the make() function:

mySlice := make([]string, 3) //a slice of 3 empty strings

You can create a new slice from an existing slice, appending one or more items to it:

mySlice := []string{"First", "Second", "Third"}

newSlice := append(mySlice, "Fourth", "Fifth")

Note that we need to assign the result of append() to a new slice, otherwise we’ll get a compiler error. The original slice is not modified, we’ll get a brand new one.

You can also use the copy() function to duplicate a slice so it does not share the same memory of the other one and is independent:

mySlice := []string{"First", "Second", "Third"}

newSlice := make([]string, 3)

copy(newSlice, mySlice)

If the slice you’re copying to does not have enough space (is shorter than the original) only the first items (until there’s space) will be copied.

You can initialize a slice from an array:

myArray := [3]string{"First", "Second", "Third"}

mySlice = myArray[:]

Multiple slices can use the same array as the underlying array:

myArray := [3]string{"First", "Second", "Third"}

mySlice := myArray[:]
mySlice2 := myArray[:]

mySlice[0] = "test"

fmt.Println(mySlice2[0]) //"test"

Those 2 slices now share the same memory and modifying one slice modifies the underlying array and causes the other slice generated from the array to be modified too.

As with arrays, each item in a slice is stored in memory in consecutive memory locations.

If you know you need to perform operations to the slice, you can request it to have more capacity than initially needed, so when you need more space, the space will be readily available (instead of finding and moving the slice to a new memory location with more space to grow and dispose via garbage collection of the old location).

We can specify the capacity adding a third parameter to make():

newSlice := make([]string, 0, 10)
//an empty slice with capacity 10

As with strings, you can get a portion of a slice using this syntax:

mySlice := []string{"First", "Second", "Third"}

newSlice := mySlice[:2] //get the first 2 items
newSlice2 := mySlice[2:] //ignore the first 2 items
newSlice3 := mySlice[1:3] //new slice with items in position 1-2
Are you intimidated by Git? Can’t figure out merge vs rebase? Are you afraid of screwing up something any time you have to do something in Git? Do you rely on ChatGPT or random people’s answer on StackOverflow to fix your problems? Your coworkers are tired of explaining Git to you all the time? Git is something we all need to use, but few of us really master it. I created this course to improve your Git (and GitHub) knowledge at a radical level. A course that helps you feel less frustrated with Git. Launching Summer 2024. Join the waiting list!
→ Get my Go Handbook

Here is how can I help you: