【问题标题】:Optimizing Sums of Parts function for Code Wars优化代码战的部分函数和
【发布时间】:2021-12-30 19:18:26
【问题描述】:

我正在查看 CodeWars 上的 Sums of Parts 问题:

让我们考虑这个例子(以一般格式编写的数组):

ls = [0, 1, 3, 6, 10]

它的以下部分:

ls = [0, 1, 3, 6, 10]
ls = [1, 3, 6, 10]
ls = [3, 6, 10]
ls = [6, 10]
ls = [10]
ls = []

相应的总和是(放在一个列表中):[20, 20, 19, 16, 10, 0]

函数parts_sums(或其在其他语言中的变体)将把一个列表 ls 作为参数,并返回一个如上定义的其各部分之和的列表。

该函数的目标是将数组元素相加,然后每次移动数组的第一个元素,直到数组的长度变为0。

我有这个解决方案:

function partsSums(ls) {
    let len = ls.length;
    let arr = [];
    for (let i = 0; i < len +1; i++) {
        arr.push(summation(ls));
        ls.shift();
    }

    function summation(a) {
        let sum = 0;
        for (let i = 0; i < a.length; i++) {
            sum += a[i];
        }
        return sum;
    }
    return arr;
}

当我在我的编辑器中运行它时它可以工作:成功完成的 CodeWars 上的所有测试用例都通过了,但是当我尝试提交时,我得到了这个错误:

进程已终止。完成时间超过 12000 毫秒

我是算法新手,不明白错误在哪里?欢迎提出任何建议。

【问题讨论】:

  • 您的算法有效,但效率太低。你认为你能找到一种更聪明的方法来解决这个问题,而无需重复地将相同的元素加在一起吗?
  • 我现在想不出其他任何解决方案,但我不知道为什么该解决方案会导致优化错误@Bergi
  • 另一种方法:; const partsSums = (ns) =&gt; [0, ...ns .reverse ()] .map (((c) =&gt; (n) =&gt; c += n) (0)) .reverse ()。提取const continualAdd = (c) =&gt; (n) =&gt; c += n 并重写为const partsSums = (ns) =&gt; [0, ...ns .reverse()] .map (continualAdd (0)) .reverse () 可能更干净

标签: javascript algorithm performance optimization


【解决方案1】:

函数的目标是对数组元素求和,然后每次移动数组的第一个元素,直到数组的长度变为0

代码挑战实际上并​​没有提到转移。通过将值立即存储在结果数组的正确索引处,您可以在不移动的情况下执行此操作。此外,您的函数summation 正在重复对一些相同的值求和。这是可以避免的。

举个例子:

ls = [0, 1, 3, 6, 10]

输出可以构造如下:

  • 创建一个长一个元素的数组,最后的值为 0:

    ls:     0  1  3  6 10
    result: .  .  .  .  .  0
    

    (此时点的值不相关)

  • 然后从右侧开始,并创建一个(向后)运行和:

    ls:     0  1  3  6 10
    result: ↓  ↓  ↓  ↓  ↓← 0
            ↓  ↓  ↓  ↓←10
            ↓  ↓  ↓←16
            ↓  ↓←19
            ↓←20
           20
    

    因此,索引 i+1 处的先前结果被添加到索引 i 处的输入中,因此它向后工作到数组的开头。

这是一个实现:

function partsSums(ls) {
    let result = Array(ls.length + 1).fill(0);
    for (let i = ls.length - 1; i >= 0; i--) {
        result[i] = ls[i] + result[i + 1];
    }
    return result;    
}

【讨论】:

  • 非常感谢 @trincot 先生的努力。现在我明白了
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-05-20
  • 1970-01-01
  • 1970-01-01
  • 2018-07-02
相关资源
最近更新 更多