FULL PYTHON FIX · 6 MIN READ
How to Fix IndexError: List Index Out of Range in Python
A list has fewer positions than your code expects. Reproduce the failure, inspect the list length, and choose a safe lookup or iteration pattern that matches the task.
Quick answer: check the index before lookup
For a nonnegative position, use 0 <= index < len(items). An index equal to len(items) is already outside the list. If you want every item, iterate over the list instead of managing positions yourself.
This check assumes index is an integer. If it comes from input(), convert the returned text with int() and handle ValueError before comparing it with numbers.
items = ['Ada', 'Bo']
index = 2
if 0 <= index < len(items):
print(items[index])
else:
print('No item at that position')Expected result: No item at that position
See why this works and test the edge casesVideo guide: How to Fix IndexError: List Index Out of Range in Python
The preview is stored on this site. YouTube loads only when you press Play. Watch on YouTube
Jump to a chapter
Read the video transcript
Select a timestamp to watch that moment on YouTube.
- 00:00
Here is a Python error that almost every beginner meets. I have a list containing Ada and Bo. The program tries to print names at index two, and Python stops with IndexError: list index out of range. The error is accurate, but it does not say which number I should use instead. We will find that from the data, then fix the program in two different ways. One fix selects a particular item; the other handles an index supplied at runtime. Along the way, we will test an empty list and show why a loop can remove the need for an index altogether. Before I run the code, predict what names at index two would mean.
- 00:40
If you read it as the second name, your answer is understandable, but Python counts list positions from zero. The first name is index zero, the second is index one, and index two would be a third name. There is no third name in this list. I will run the unmodified code now so we have a concrete failure to diagnose. Notice that the exception points to the square-bracket expression. The list was created successfully. We need to inspect the requested position, not rewrite the entire program. The length of this list is two because it contains two items. That is a count, not the final index. Enumerate shows the actual pairs: zero with Ada, one with Bo.
- 01:24
For a list with n items, the valid nonnegative indexes are zero up to n minus one. Therefore a valid nonnegative position must be less than len of the list, not less than or equal to it. If the requested index equals the length, it is already one step beyond the end. That small difference between less than and less than or equal to is the source of many off-by-one bugs. The last line demonstrates a different feature: index negative one selects the final item. Negative two would select Ada here. Python allows negative indexes when you intentionally count back from the end. But I would not change an unknown invalid index to negative one just to silence the error.
- 02:10
It would select the last item even if the caller wanted something else. The right fix depends on what the program is trying to do. The useful debugging habit is to print the actual collection, its length, and the requested index. Once you can state the valid range aloud, the traceback becomes much easier to understand. If I know that I want the second name in this exact list, I can use index one directly. In a real program, though, the requested index may come from a menu, a file, or a calculation. Then I should check it before using the square brackets. This condition says requested must be at least zero and strictly smaller than the number of names.
- 02:52
On the first run, requested is two. The list length is also two, so the condition is false and the program prints a helpful message instead of throwing an exception. Now I change requested to one. The condition is true and Python prints Bo, as intended. We have chosen to reject negative positions, even though Python accepts some of them. That is a user-interface decision: if a menu numbers items from zero, a negative menu selection may be confusing. Another application might deliberately support negative indexes. The important point is to make that rule explicit. I could catch IndexError around the lookup, but that would mix ordinary validation with an exception handler.
- 03:38
A simple boundary condition is clearer for this menu behavior. It also tells the reader which indexes the application promises to accept. Sometimes there is no reason to select one position at all. If the task is to process every name, iterate over the names directly. I am using enumerate because I want to display each position as well as the value. If I only needed the names, I would write for name in names and omit the index completely. This is safer than writing a loop with a manually updated counter and then looking up names at that counter. The loop gets the values that actually exist. Let us change the list to an empty list and run again.
- 04:21
There is no output and no exception. That is sensible: there were no names to visit. An index lookup such as names at zero would have failed on this empty list. A loop does not invent a position that is not present. This distinction helps you choose between three patterns. A literal index is appropriate when you know a particular position exists. A checked index is appropriate when a caller chooses a position. Direct iteration is appropriate when you want to work through the whole collection. Picking the pattern that matches the task prevents the same error from reappearing later. A single successful lookup does not prove that a boundary fix is correct.
- 05:03
This small test tries the first valid index, the final valid index, an index equal to the length, and an empty list. Ada and Bo are returned for the valid requests. The other two requests return our chosen fallback, missing. If I had used a less-than-or-equal sign in the condition, the request at index two would still reach the square brackets and raise IndexError. That is why the boundary tests matter. On the website, the practice task asks you to write pick_color. It should return a color for a valid nonnegative position and the word unknown otherwise. Test zero, one, two, negative one, and an empty list.
- 05:43
Think about why negative one is rejected in that particular task, even though Python can use it to select the last item. Write down the valid range before writing the condition. When you encounter an IndexError in your own code, do not guess a new number until you inspect the list. Print its length, print the requested index, and decide whether you need a checked lookup or a loop. That gives you a fix grounded in the actual data rather than a change that only happens to work for today's example. The full guide and related interactive lessons are linked below the video.
Ask for a position that does not exist
Run the short program below. The list contains two names, yet the code asks for position 2. Python raises IndexError at the square-bracket lookup. The list itself is valid; the requested position is the problem.
Positive list indexes start at zero. A two-item list therefore has positions 0 and 1. Position 2 would be the third item, which has not been added. This is often called an off-by-one error because the programmer mistakes the number of items for the position of the final item. Read the failing line and inspect the actual list before changing the index.
names = ['Ada', 'Bo']
print(names[2])IndexError: list index out of rangeCompare the requested index with the list length
Print the list, its length, and each available index. enumerate() pairs every item with its actual position, removing the need to guess. For this list, len(names) is 2, but the largest valid positive index is len(names) - 1, or 1. The valid condition is 0 <= index < len(names). The upper bound is strict: an index equal to len(names) is already outside the list.
Negative indexes have separate meaning in Python. -1 selects the last item and -2 selects the item before it. They are useful when you deliberately want an item relative to the end, but replacing every failing index with -1 may hide a mistake. Diagnose what the program is trying to select first.
names = ['Ada', 'Bo']
print('length:', len(names))
for index, name in enumerate(names):
print(index, name)
print('last:', names[-1])length: 2
0 Ada
1 Bo
last: BoUse a valid index or guard a variable index
If you mean the second item of a known two-item list, use index 1. If the index comes from a user, file, or calculation, validate it before lookup. Decide whether negative indexes are allowed. The example below accepts only nonnegative positions and prints a helpful message for any other value.
If your real goal is to process every item, stop calculating indexes and iterate over the items directly. Use enumerate(names) only when you need both the item and its position. This also works for an empty list: the loop runs zero times without trying an invalid lookup.
names = ['Ada', 'Bo']
requested = 2
if 0 <= requested < len(names):
print(names[requested])
else:
print('No name at that position')No name at that positionnames = ['Ada', 'Bo']
for index, name in enumerate(names):
print(index, name)0 Ada
1 BoTest the first, last, and missing positions
A fix that only works for index 1 is fragile. Test index 0, the last valid index, an index equal to the list length, and an empty list. These are the boundaries where off-by-one errors appear. The helper below returns a value for a valid nonnegative index and a clear fallback for a missing one.
The fallback is a design choice, not a universal rule. In some applications a missing item should raise an exception so the caller knows the data is broken. In an interactive menu, showing a message may be better. Avoid a broad except block that quietly hides mistakes unrelated to indexing.
def choose(items, index):
if 0 <= index < len(items):
return items[index]
return 'missing'
print(choose(['Ada', 'Bo'], 0))
print(choose(['Ada', 'Bo'], 1))
print(choose(['Ada', 'Bo'], 2))
print(choose([], 0))Ada
Bo
missing
missing- For a list of length n, nonnegative indexes range from 0 through n - 1.
- Test an index equal to n; it must be rejected.
- Iterate over values, or use enumerate() for positions and values, when processing the whole list.
Practice the fix
Write pick_color(colors, position). Return the color for a valid nonnegative position, or 'unknown' otherwise. Try ['red', 'blue'] with positions 0, 1, 2, and -1, then try an empty list. Explain why the upper boundary uses < rather than <=.
Need a hint?
The nonnegative valid range is 0 <= position < len(colors). Return colors[position] only inside that branch. Decide deliberately whether -1 should be rejected.
Python console
Ready to runEdit the code and run it in your browser. Examples above can be loaded with Try this example.
Does your code use input()? Add one value per line
Your output appears here.
Write your solution, then select Check practice.
Key takeaways
- List indexes start at zero; the last positive index is len(items) - 1.
- Check 0 <= index < len(items) when the caller should supply a nonnegative position.
- Negative indexes are valid only when they match the intended behavior.
- Use direct iteration or enumerate() instead of a manually managed index for whole-list work.