I am doing a coding exercise: Given a sequence of integers as an array, determine whether it is possible to obtain a strictly increasing sequence by removing no more than one element from the array.
So I wrote this code:
def almostIncreasingSequence(sequence):
first_list, second_list = sequence, sequence
for i in range(len(sequence)-1):
if sequence[i] >= sequence[i+1]:
first_list.remove(sequence[i])
second_list.remove(sequence[i+1])
break
if first_list == sorted(set(first_list)) or second_list == sorted(set(second_list)):
return True
else:
return False
Now this code seems to work on most sequences but this one in particular raises an error:
print almostIncreasingSequence([1,3,2])
The error is as following:
Traceback (most recent call last):
file.py3 on line ?, in getUserOutputs
userOutput = _runsppge(testInputs[i])
file.py3 on line ?, in _runsppge
return almostIncreasingSequence(*_fArgs_lujxeukjlbwc)
file.py3 on line 7, in almostIncreasingSequence
second_list.remove(sequence[i+1])
IndexError: list index out of range
I just dont understand how the list index could possibly be out of range.. Anyone got a clue?
Since you are removing items from the same list which you are iterating on
for i in range(len(sequence)-1):
if sequence[i] >= sequence[i+1]:
first_list.remove(sequence[i]) # <-- removing item
second_list.remove(sequence[i+1]) # <-- removing item
break
And, as mentioned in the comments, first_list, second_list = sequence, sequence
doesn't create any new lists. first_list, second_list,
and sequence
all refer to the exact same list object after that line.
EDITED
The list after the first removal ( first_list.remove(sequence[i])
), has one less element, hence if the i+1
in on the edge at that moment, it would get out of bound.
Think of a list like [1, 2, 3, 5, 4]
. The if
statement is triggered when i
is at the element 5
(i is 3), then the first removal ( first_list.remove(sequence[i])
) takes place, after that statement, list has 4 elements [1, 2, 3, 4]
, and the next line tries to access the element (element 4) at i+1
( second_list.remove(sequence[i+1])
), hence it gets (i is 4) out of bound.
> c:\users\jeffrey\documents\github\wadi\example.py(4)almostIncreasingSequence()
3 for i in range(len(sequence)-1):
----> 4 if sequence[i] >= sequence[i+1]:
5 first_list.remove(sequence[i])
ipdb> next
> c:\users\jeffrey\documents\github\wadi\example.py(5)almostIncreasingSequence()
4 if sequence[i] >= sequence[i+1]:
----> 5 first_list.remove(sequence[i])
6 second_list.remove(sequence[i+1])
ipdb> first_list
[1, 3, 2]
ipdb> second_list
[1, 3, 2]
ipdb> next
> c:\users\jeffrey\documents\github\wadi\example.py(6)almostIncreasingSequence()
5 first_list.remove(sequence[i])
----> 6 second_list.remove(sequence[i+1])
7 break
ipdb> first_list
[1, 2]
ipdb> second_list
[1, 2]
ipdb>
Even if I didn't execute this line second_list.remove(sequence[i+1])
, because first_list
and second_list
point to the same location. In other words we can say that one is an alias of the other. So that if one can change then second_list get change also.
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.