Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

replacing item in list while iterating

From Google's Python Class

#!/usr/bin/python -tt
# Copyright 2010 Google Inc.
# Licensed under the Apache License, Version 2.0
# http://www.apache.org/licenses/LICENSE-2.0

# Google's Python Class
# http://code.google.com/edu/languages/google-python-class/

# Additional basic list exercises

# D. Given a list of numbers, return a list where
# all adjacent == elements have been reduced to a single element,
# so [1, 2, 2, 3] returns [1, 2, 3]. You may create a new list or
# modify the passed in list.
def remove_adjacent(nums):
  x = 0
  newlist = []
  for x in range(0,len(nums),1):
    if nums[x] == nums[x+1]:
      newlist.append(nums[x])
      x = x+2
    else:
      newlist.append(nums[x])
      x = x+1

  return nums

it is giving me an error saying that the list index is out of range but I am not sure what is wrong. I read somewhere that you cannot replace values in a list while iterating using a for loop but have no idea how to fix that. Any advice would be appreciated.

like image 600
Arun Kalyanaraman Avatar asked Oct 24 '25 05:10

Arun Kalyanaraman


2 Answers

Its probably due to nums[x+1] being out of range. x only goes from 0 to len(nums) - 1 meaning that when x is len(nums)-1, you will essentially be indexing into nums[len(nums)] which will be one past the end of nums (remember the last index in a non-empty list is 1 less than its length, since we start counting indexes from 0).

like image 91
Preet Kukreti Avatar answered Oct 26 '25 18:10

Preet Kukreti


The index x+1 will be out of range when x is the index of the very last element. In addition, you are creating a new list yet you return the old one.

Modifying the value of x isn't doing what you think as it is being reset at every loop iteration.

Here is an alternative implementation:

def remove_adjacent(nums):
  newlist = []
  for i in range(0, len(nums)):
    if i == len(nums) - 1:      # Avoid out of range error.
      newlist.append(nums[i])
    elif nums[i] == nums[i+1]:  # Skip until the last repeat
      continue
    else:  
      newlist.append(nums[i])
  return newlist