Start learning free

LESSON 92 OF 348 · ARRAYS I

Accessing List Elements in Kotlin: Index and get()

Lesson Read the full explanation

We can access the data inside an ArrayList using indexes and the .get() method.

ArrayLists also use zero-based indexing, so the first element in an ArrayList has an index of 0.

val array = mutableListOf(50, 60, 70)

println(array[0]) // Output: 50

val data = array[1]
println(data) // Output: 60

Assignment
Follow the Coding Tutorial and let's play with some arrays.


Hint
Look at the examples above if you get stuck.


STEP 1 OF 3
    Ctrl + Enter to check

    KOTLIN · ARRAYS I

    Accessing Elements in Kotlin, explained

    Reading an element of a list

    A Kotlin list keeps its elements in order, and each has an index starting at 0. To read the element at an index, put the index in square brackets after the list's name. The brackets are shorthand for the list's get method, so list[1] and list.get(1) do the same thing. Square brackets are the form Kotlin programmers normally write.

    val array = mutableListOf(50, 60, 70)
    
    println(array[0])
    val data = array[1]
    println(data)
    println(array.get(2))
    
    50
    60
    70
    

    The first element is at index 0, so a list with 3 elements has valid indices 0, 1 and 2. Reading any other index throws an IndexOutOfBoundsException.

    Using the value

    The result of array[1] has the list's element type. For a MutableList<Int> it is an Int, which you can store in a variable, as data does above, or use directly in an expression.

    Why counting starts at zero

    An index is best read as an offset: how many steps you are from the start of the list. The first element is zero steps from the start, so it is at index 0, and the last element of a list with n items is at index n - 1. Thinking of the index as a distance, rather than as a place in a queue, makes off-by-one mistakes less likely.

    Index and element types

    The index is always an Int. The element has the type the list was declared with, so the compiler knows what you get back before the program runs. In a MutableList<String> every indexed read is a String, and storing one in an Int variable doesn't compile.

    The exercise

    The starter code creates two lists:

    val fruits = mutableListOf("mango", "kiwi", "grapefruit")
    val ages = mutableListOf(14, 32, 50, 21)
    
    1. Print the second fruit. Use index 1. It prints kiwi.
    2. Print the sum of the first three ages. Put the three indexed values in one expression inside println. Kotlin works out 14 + 32 + 50 first and prints 96.
    3. Print the last age minus the first. There are four numbers, so the last index is 3, giving 21 - 14 and the output 7.
    val fruits = mutableListOf("mango", "kiwi", "grapefruit")
    val ages = mutableListOf(14, 32, 50, 21)
    
    println(fruits[1])
    println(ages[0] + ages[1] + ages[2])
    println(ages[3] - ages[0])
    
    kiwi
    96
    7
    

    Reading never changes the list

    Reading an element leaves the list exactly as it was, so you can read the same index as often as you like. The one thing to watch is that the index is valid. If it comes from a calculation, such as ages.size - 1, make sure the calculation can't produce a value below 0 or at least the size. Kotlin also offers getOrNull(index), which returns null instead of throwing when the index is outside the list.

    Indexing is also quick: reading an element of an ArrayList takes the same time whether it is at index 0 or at index 100,000, because the list is stored as a block of consecutive slots.

    Common mistakes

    • Counting from 1. The second item is at index 1. fruits[2] is the third, grapefruit.
    • Reading past the end. In a list of 4 items, ages[4] throws IndexOutOfBoundsException. In general the last index is the size minus one.
    • Negative indexes. Kotlin doesn't count from the end with negative numbers. ages[-1] throws; use ages.last() or ages[ages.size - 1].
    • Printing the whole list. println(ages) prints all of it: [14, 32, 50, 21]. Add the index when you need one element.

    Visiting every element

    Indexing combines well with a loop. A list's indices property is the range of valid positions, so a loop over it never goes out of bounds:

    val fruits = mutableListOf("mango", "kiwi")
    for (i in fruits.indices) {
        println("$i: ${fruits[i]}")
    }
    println(fruits[1].uppercase())
    println(fruits.first())
    
    0: mango
    1: kiwi
    KIWI
    mango
    

    The element fruits[1] is a String, so string functions such as uppercase() work on it. The function first() is a readable shortcut for fruits[0], and last() is the one for the final element.

    Key takeaways

    • List indices start at 0 and end at size - 1.
    • list[i] is shorthand for list.get(i).
    • An indexed element is an ordinary value, so it works in arithmetic and in println.
    Keep going with KotlinAbout 340 step-by-step lessons, from your first line of code to coding interviews. Free to start.
    Start learning free