## How to Access Index in Python's for Loop

### Introduction

Python is a very high-level programming language, and it tends to stray away from anything remotely resembling internal data structure. Because of this, we usually don't really need indices of a list to access its elements, however, sometimes we desperately need them.

In this article, we will go over different approaches on how to access an index in Python's for loop.

### How to Access Index in Python's for Loop?

The easiest, and most popular method to access the index of elements in a for loop is to go through the list's length, increasing the index. On each increase, we access the list on that index:

my_list = [3, 5, 4, 2, 2, 5, 5]

print("Indices and values in my_list:")

for index in range(len(my_list)):
print(index, my_list[index], end = "\n")


Here, we don't iterate through the list, like we'd usually do. We iterate from 0..len(my_list) with the index. Then, we use this index variable to access the elements of the list in order of 0..n, where n is the end of the list.

This code will produce the output:

Indices and values in my_list:
0 3
1 5
2 4
3 2
4 2
5 5
6 5


### Using enumerate()

enumerate() is a built-in Python function which is very useful when we want to access both the values and the indices of a list. It's worth noting that this is the fastest and most efficient method for acquiring the index in a for loop.

This method adds a counter to an iterable and returns them together as an enumerated object. This enumerate object can be easily converted to a list using a list() constructor. This is the most common way of accessing both elements and their indices at the same time.

Now, let's take a look at the code which illustrates how this method is used:

my_list = [3, 5, 4, 2, 2, 5, 5]
print("Indices and values in my_list:")
for index, value in enumerate(my_list):
print(list((index, value)))


This code will produce the output:

Indices and values in my_list:
[0, 3]
[1, 5]
[2, 4]
[3, 2]
[4, 2]
[5, 5]
[6, 5]


What we did in this example was enumerate every value in a list with its corresponding index, creating an enumerate object. Then, we converted that enumerate object into a list using the list() constructor, and printed each list to the standard output.

Additionally, you can set the start argument to change the indexing. Currently, it's 0-based. Let's change it to start at 1 instead:

my_list = [3, 5, 4, 2, 2, 5, 5]
print("Indices and values in my_list:")
for index, value in enumerate(my_list, start=1):
print(list((index, value)))


Now, this produces:

Indices and values in my_list:
[1, 3]
[2, 5]
[3, 4]
[4, 2]
[5, 2]
[6, 5]
[7, 5]


### Using List Comprehensions

A list comprehension is a way to define and create lists based on already existing lists. It's usually a faster, more elegant, and compact way to manipulate lists, compared to functions and for loops.

Every list comprehension in Python contains these three elements:

1. iterable - A collection who's elements we can inspect one at a time
2. member - Value or object in a list (which is an iterable)
3. expression - Can be any valid expression that returns a value(a member, an iterable, a call to a function...)

Let's take a look at the following example:

my_list = [1, 2, 3, 4, 5]
my_list_squared = [m*m for m in my_list]
print(my_list_squared)


This code will produce the output:

[1, 4, 9, 16, 25]


In this list comprehension, my_list represents the iterable, m represents a member and m*m represents the expression.

Now that we went through what list comprehension is, we can use it to iterate through a list and access its indices and corresponding values. Let's take a look at this example:

my_list = [3, 5, 4, 2, 2, 5, 5]
print("Indices and values in my_list:")
print([list((i, my_list[i])) for i in range(len(my_list))])


This code will produce the output:

Indices and values in my_list:
[[0, 3], [1, 5], [2, 4], [3, 2], [4, 2], [5, 5], [6, 5]]


What we did in this example was use the list() constructor. This constructor takes no arguments or a single argument - an iterable. This includes any object that could be a sequence (string, tuples) or a collection (set, dictionary).

If no parameters are passed, it returns an empty list, and if an iterable is passed as a parameter it creates a list consisting of its items.

We constructed a list of two element lists which are in the format [elementIndex, elementValue] . These two-element lists were constructed by passing pairs to the list() constructor, which then spat an equivalent list.

This will create 7 separate lists containing the index and its corresponding value in my_list that will be printed.

### Using zip()

The zip() function accepts two or more parameters, which all must be iterable.

It returns a zip object - an iterator of tuples in which the first item in each passed iterator is paired together, the second item in each passed iterator is paired together, and analogously for the rest of them:

list_a = [1, 2, 3]
list_b = ['A', 'B', 'C']

# Zip will make touples from elements with the same
# index (position in the list). Meaning that 1 from the
# first list will be paired with 'A', 2 will be paired
# with 'B' and so on...
for elem1,elem2 in zip(list_a,list_b):
print((elem1,elem2))


Running the code snippet above we get:

(1, 'A')
(2, 'B')
(3, 'C')


The length of the iterator that this function returns is equal to the length of the smallest of its parameters.

Now that we've explained how this function works, let's use it to solve our task:

my_list = [3, 5, 4, 2, 2, 5, 5]
print ("Indices and values in my_list:")
for index, value in zip(range(len(my_list)), my_list):
print((index, value))


This code will produce the output:

Indices and values in my_list:
(0, 3)
(1, 5)
(2, 4)
(3, 2)
(4, 2)
(5, 5)
(6, 5)


In this example, we passed a sequence of numbers in the range from 0 to len(my_list) as the first parameter of the zip() function, and my_list as its second parameter. The function paired up each index with its corresponding value, and we printed them as tuples using a for loop.

If we wanted to convert these tuples into a list, we would use the list() constructor, and our print function would look like this:

print(list((index, value)))


### Conclusion

In this article we went through four different methods that help us access an index and its corresponding value in a Python list.

Besides the most basic method, we went through the basics of list comprehensions and how they can be used to solve this task. Even though it's a faster way to do it compared to a generic for loop, we should generally avoid using it if the list comprehension itself becomes far too complicated. Complicated list comprehensions can lead to a lot of messy code.

It is important to note that even though every list comprehension can be rewritten in a for loop, not every for loop can be rewritten into a list comprehension.

Another two methods we used were relying on the Python in-built functions: enumerate() and zip(), which joined together the indices and their corresponding values into tuples. Then, we converted those tuples into lists and printed them on the standard output.