【问题标题】:Conditional while loop to calculate cumulative sum?有条件的while循环来计算累积和?
【发布时间】:2020-12-20 07:25:44
【问题描述】:

我想写一个函数,它接受一个数字列表并返回累积和;也就是说,一个新列表,其中第 i 个元素是原始列表中前 i+1 个元素的总和。例如[1, 2, 3]的累计和为[1, 3, 6]。

到目前为止,这是我的代码:

 def count(list1):
     x = 0
     total = 0
     while x < len(list1):
         if x == 0:
             total = list1[0]
             print total
             x = x +1
         else:
             total = list1[x] + list1[x -1]
             print total
             x = x + 1
     return total 

print count([1, 2, 3, 4, 7])

但是,它不起作用。

你能告诉我我做错了什么吗?我已经为此工作了很长时间。

【问题讨论】:

  • 这段代码比它需要的复杂得多:/
  • “我不是很聪明。”不要将缺乏经验与缺乏智慧混为一谈,或者担心我们会混淆他们,因此觉得你必须为不理解某些事情事先道歉。每个人都曾经是初学者,而且人们并不是天生就懂 Python。还没有,反正..
  • ++1! @DSM 的评论..人们似乎经常忘记这一点(而且经常在这里)
  • 感谢您的评论,帝斯曼。你真好。

标签: python while-loop cumulative-sum


【解决方案1】:

你可能有点过度思考这个过程。逻辑不需要真正分解成这样的案例测试。到目前为止,您拥有的部分是总计数器,但您应该只需要遍历列表中的每个值。不做有条件的while,用if..else

通常我不会只给出答案,但我觉得看到工作代码对你来说比尝试经历你目前为止额外和不必要的麻烦更有益。

def count(l):
    total = 0
    result = []
    for val in l:
        total += val
        result.append(total)
    return result

我们仍然使用总计数器。我们为我们的结果创建了一个空列表。但是我们所要做的就是遍历列表中的每个项目,添加到总数中,然后每次都附加新值。没有条件,您不必担心while 何时会中断。循环遍历原始列表中的每个项目是一致的。

【讨论】:

  • 非常感谢您的回答!这很有道理!我正在阅读《Think Python: How to Think Like a Computer Scientist》一书,到目前为止,我已经学到了所有这些东西。再次非常感谢!你真的很有帮助!
  • @LukeD:没问题!我认为这与您迄今为止可能已经介绍过的术语非常接近。祝你好运!如果您需要对此进行更多说明,请告诉我。
  • 我会的,先生。再次感谢,你真的很有帮助。正如你所做的那样,我不得不以不同的方式思考这个问题。谢谢。
【解决方案2】:

在这里,您将当前索引与最后一个索引相加并覆盖“total”

total = list1[x] + list1[x -1]

我猜你想要这样的东西,它会为下面的列表返回 31。

def count(list1):
     x = 0
     total = 0
     while x < len(list1):
         total += list[x]
         print total
         x = x + 1
     return total

list = [1, 2, 4, 8, 16]
print count(list)

【讨论】:

  • 感谢您的评论!这很有帮助!谢谢!
  • 您在问题的代码中发现了一个潜在问题。但是,您的函数返回列表内容的总和,而不是问题中要求的具有累积总和的新列表。
【解决方案3】:

一种简单的方法可以是

>>> given_list = [1, 4, 5, 8]
>>> output_list = [sum(given_list[:num]) for num in range(len(given_list)+1)]
>>> output_list
[0, 1, 5, 10, 18]
>>> output_list[1:]
[1, 5, 10, 18]
>>> 

看看这是否适用于不同类型的列表。我把它留给你。

【讨论】:

  • 这对初学者来说太复杂了,而且无法想象 OP 会得到它。
  • 我很惭愧以这种方式尝试解决方案。
  • 谢谢你的建议,pyfunc。这对我来说有点太复杂了,但谢谢你的帮助。如果我再聪明一点,我相信我会理解得更好!
  • @LukeD:有很多非常有趣的方法可以用更少的代码计算东西。你最终会遇到列表推导。
  • @LukeD:这根本不是关于聪明。它是关于学习、坚持和努力的。我想我们都可以尝试。在 SO 的帮助下,学习可以变得愉快
【解决方案4】:

使用total,您并没有完全按照自己的意愿行事。

您将total 设置为list[x] + list[x+1]。您真的希望它是 所有 先前元素和当前元素的总和。

将total = list1[x] + list1[x-1] 替换为total += list1[x]。

【讨论】:

  • 感谢您的建议!我试过了,但它不起作用。但它确实有帮助,谢谢!
【解决方案5】:

你不需要编写这个函数。它被放置在 itertools 模块中:

>>> list(itertools.accumulate([1,2,3]))
[1, 3, 6]

【讨论】:

  • 我认为与此简洁代码一起进行的解释会有所帮助
  • @Levon 函数的名称(accumulate)是不言自明的。因为它是一个生成器,所以我给它打了电话list
  • 是的,我知道..考虑到 OP 的问题,我认为向他们提供一些最小的(例如,1 行)解释会很有帮助 - 仅此而已:)不是每个人都对我们的“pythonic”方式感到满意......
【解决方案6】:

这是我想出的解决方案:

def count(list1):
     total = 0
     old = 0
     for position, x in enumerate(list1):
         total = x + old
         old = x
         print total
     return


count([1,1,2,3,5,8,13])

【讨论】:

    【解决方案7】:

    另一种解决方案,单线,但绝对有效 (http://ideone.com/qtwh7),尽管多线解决方案更清楚地了解此处实际发生的情况:

    data = [3, 7, 22, -3, 5, -23, 16]
    
    result = reduce(lambda a, b: a+[a[-1]+b], data, [0])[1:]
    
    print result
    

    【讨论】:

    • 这可以在没有连接的情况下完成:reduce(lambda r, x: r.append(r[-1] + x) or r, data, [0])[1:] 甚至没有索引reduce(lambda (res, sum), x: (res.append(sum + x) or res, sum + x), data, ([], 0))[0]
    • 我使用len(data) == 1000 的第一个(第二个)变体速度提高了 7(6) 倍,并且内存效率更高:)
    • @astynax:你可能是对的,但对我来说这看起来很奇怪;)它是什么数量级,快 7 倍或 76 倍? ;) 不过,您可以尝试以类似的方式使用map()。它可能(应该?)更快。
    • 第一 - 快 7 倍,第二 - 快 6 倍。使用 len(data) == 10000:第一 - 快 45 倍,第二 - 35 :)
    【解决方案8】:

    我做了同样的练习,下面是我的解决方案。它仅使用基本的append 列表方法和slice 列表运算符。

    def accum(list):
        """Sequential accumulation of the original list"""
        result = []
        for i in range(len(list)):
            result.append(sum(list[:i+1]))
        return result
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2019-07-08
      • 2023-01-18
      • 2014-02-16
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-12-02
      • 1970-01-01
      相关资源
      最近更新 更多