in C is an alias for its reference/pointer unlike Go array. • C arrays are passed to function as a pointer whereas in Go unless explicitly stated, array is passed by values. • In C, array cannot be copied like arr1 = arr2 unless arr1 and arr2 are pointers. This is possible in Go. • In C, an array which is dynamically allocated should be freed. Go supports garbage collection.
dynamically grow unlike Go arrays. • The size of the GO slice need not be known at compile time unlike Go arrays. • Go array would end up in stack since the size is known at compile time but Go slice is most likely to end up in heap. • Go slice is a 3 word data structure <pointer, length, capacity> unlike Go arrays. • Go array slice playground
contiguous blocks of memory. • Slice can grow with in-built append function and can be shrunk by slicing out part of the underlying array. • Slice can be efficiently accessed, iterated and garbage collected since it represents a contiguous blocks of memory. • Slice are three word (24 bytes) data structure as below with pointer to the backing array, length and capacity.
as follows • Make Slice Make playground • Literals Slice Literals playground • Nil slice can be created as `var slice [] int` (Zero value is nil) • Empty slice can be created as `slice := make([] int, 0)` or `slice := []int{}`
Create a new slice from #1 starting from index 1 & length = 2 • Now change the index 1 of the new slice • Print both the slices and check • Template Exercise 1 template • Solution Exercise 1 solution
can be increased dynamically with in-built append function. • The append function takes in a source slice and append values and returns a new slice • Append always increases the length of the new slice but capacity may or may not increase depending on the available capacity of the new slice. • Slice append Slice append len < cap playground
efficient way to implement dynamic arrays is to double the size of the copy array when the size hits the capacity. • The cost is amortised because the capacity is doubled when the size is a power of 2 • E.g., Let X be the size of the dynamic array. The array would have doubled its size at size = 1,2,4,8,16,32…X. • So the time complexity for inserts would be 1 + 2 + 4 + 8 + 16 +…..X • => x + x/2 + x/4 + x/8 which is roughly 2X • Time complexity for inserts = O(2X) where X is size of the array
== capacity then the new slice is given a new backing array with double the original size • In Go built in append utilise amortised cost to increase the capacity in efficient manner • Slice append len == cap amortized playground
the slice restricts the capacity. • slice := source[2:3:4] • By setting the capacity == length, the new slice is forced to detach from the source backing array and creates its own backing array • The above technique is used in scenarios where we just want to modify the new slice backing array without changing the source backing array.
Create a new slice from above source at index 2 and length as 3 • Can we append a string to the new slice without changing the original slice? • Slice exercise 3 template playground • Slice exercise 3 solution playground
keyword or with index. • Slice iterate range playground • Slice iterate index playground • Iterating by index can be used to start iteration from any random index.
be composed to create multidimensional slices. • Slice multidimensional playground • Iterating by row is more efficient then column in multidimensional array because of contiguous access pattern (predictable access pattern)
is pass by value i.e., 3 word value or 24 bytes • Since only the pointer to the backing array is passed, this is very efficient. Whether the size of the backing array is 10 or one million only 24 bytes are passed to function. • This is very similar to how C array’s are passed between functions. • Slice passing function playground