【问题标题】:replacing item in list while iterating迭代时替换列表中的项目
【发布时间】:2013-06-14 23:39:10
【问题描述】:

来自 Google 的 Python 类

#!/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

它给我一个错误,说列表索引超出范围,但我不确定出了什么问题。我在某处读到,在使用 for 循环进行迭代时无法替换列表中的值,但不知道如何解决。任何建议将不胜感激。

【问题讨论】:

    标签: python python-2.7


    【解决方案1】:

    这可能是因为nums[x+1] 超出范围。 x 只从 0len(nums) - 1,这意味着当 xlen(nums)-1 时,您实际上将索引到 nums[len(nums)],这将是 nums 末尾的一个后(记住最后一个索引在非空列表的长度小于1,因为我们从0 开始计算索引)。

    【讨论】:

    • +1,这至少回答了 this 问题。还有一些其他错误,但它们可能应该是一个新问题
    【解决方案2】:

    当 x 是最后一个元素的索引时,索引 x+1 将超出范围。此外,您正在创建一个新列表,但您返回了旧列表。

    修改x 的值并没有按照您的想法进行,因为它在每次循环迭代时重置

    这是一个替代实现:

    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    
    

    【讨论】:

    • 谢谢,我不知道。
    • 别担心,我第一次看到这个问题时也是这么想的。
    【解决方案3】:

    索引x+1超出列表的最后一个元素的范围,其索引为len(nums)-1--没有nums[len(nums)]

    itertools模块中使用groupby()函数真的很简单:

    from itertools import groupby
    
    def remove_adjacent(nums):
        return [k for k, _ in groupby(nums)]
    
    print remove_adjacent([1, 2, 2, 2, 3])
    

    输出:

    [1, 2, 3]
    

    【讨论】:

    • +1,我猜[1, 2, 2, 2, 3] 的正确答案不是[1, 2, 2, 3]
    • @gnibbler:这就是我如何解释“所有相邻的 == 元素都已简化为单个元素”。
    【解决方案4】:

    您也可以使用 zip 和列表推导来做到这一点:

    def remove_adjacent(nums):
        return [n[0] for n in zip(nums, nums[1:]) if n[0] != n[1]]
    

    【讨论】:

    • 您应该只使用!= 表示不相等,因为<> 已从Python3 中删除
    猜你喜欢
    • 1970-01-01
    • 2014-10-26
    • 2019-12-02
    • 2020-05-27
    • 1970-01-01
    • 1970-01-01
    • 2012-11-11
    • 2021-03-06
    相关资源
    最近更新 更多