Python Forum

Full Version: Index out of range error
You're currently viewing a stripped down version of our content. View the full version with proper formatting.
Hi Everyone,
I am trying to create a sublist which uses a while loop to return a sublist of the input list. The sublist should contain the same values of the original list up until it reaches the number 5 (it should not contain the number 5).
I am able to acheive that using the below code but getting Index Error: List index out of range.

def sublist(l):
my_list= []
idx= 0
while l[idx]!= 5:
my_list.append(l[idx])
idx= idx+1
return my_list
p= [3,4,2,43,5,6]
print(sublist(p))
I appreciate any help on this.

Thanks,
Shikha
First - this code runs ok on my machine if intentation is fixed.

>>> def sublist(l):
...     my_list= []
...     idx= 0
...     while l[idx]!= 5:
...         my_list.append(l[idx])
...         idx= idx+1
...     return my_list
...
>>> p = [3,4,2,43,5,6]
>>> print(sublist(p))
[3, 4, 2, 43]
However, this is very complicated solution. You know the number which should break the original list to sublist. You can get index of that number and make slice:

>>> new = p[:p.index(5)]
>>> new
[3, 4, 2, 43]
If there is no 5 in the list then ValueError will be raised. If there is possibility that it could happen then it should be wrapped into try..except.

EDIT: now I get it. IndexError will be raised when there is no 5 in list. It logical as index is incremented until 5 is encountered.

You should use for loop instead of while:

>>> def sublist(l):
...     my_list = []
...     for el in l:
...         if el == 5:
...             break
...         else:
...             my_list.append(el)
...     return my_list
...
>>> p = [3,4,2,43,6]
>>> sublist(p)
[3, 4, 2, 43, 6]
>>> p = [3,4,2,43,5,6]
>>> sublist(p)
[3, 4, 2, 43]
With index and slicing it could be:

>>> def sublist(l, *, breaker=5):
...     try:
...         return l[:l.index(breaker)]
...     except ValueError:
...         return l[:]                   
...
>>> p = [3,4,2,43,6]
>>> sublist(p)
[3, 4, 2, 43, 6]
>>> p = [3,4,2,43,5, 6]
>>> sublist(p)
[3, 4, 2, 43]
>>> sublist(p, breaker=2):
[3, 4]
Taking of advantage built-in iter() function and combining it with functools.partial one can extract sublist with unreadable oneliner:

>>> from functools import partial
>>> p = [3, 4, 2, 43, 5, 6]
>>> list(iter(partial(next, iter(p)), 5))
[3, 4, 2, 43]
Slightly more readable as function:

>>> from functools import partial
>>> def sublist(l, *, breaker=5):
...     give_me_next_in_list = partial(next, iter(l))
...     return list(iter(give_me_next_in_list, breaker))
...
>>> sublist([3, 4, 2, 43, 5, 6])
[3, 4, 2, 43]
>>> sublist([3, 4, 2, 43, 6])
[3, 4, 2, 43, 6]