【问题标题】:sum values in a range of indices with O(1) complexity [closed]对具有 O(1) 复杂度的一系列索引中的值求和 [关闭]
【发布时间】:2016-10-28 20:11:41
【问题描述】:

我们得到一个整数向量 (V[]) 和两个索引值,AB。我们需要将V[A]V[B] 之间的所有整数相加。

例如,

V[] == {0, 1, 2, 0, 4, 0, 3}, A == 2, B == 6
Sum == V[3] + V[4] + V[5] == 4

是否可以用O(1) 复杂性来解决? 我考虑过使用内存地址操作,但我仍然不确定它是如何工作的(例如:将下一个(B-A) 地址值与&V[A] 相加)

【问题讨论】:

  • 你认为这会怎样?
  • 完全不可能。如果你想要 O(1) 访问范围和,你应该预处理你的数据并构建一个前缀和的向量或类似的东西。
  • 通常当这个问题被问到时,上下文允许对输入进行预处理。 IE。你有一个从向量构造的类,然后是一个查询方法。唯一通常的要求是查询是O(1),但构造可以更多。
  • 不,不是没有预处理。您可以简单地存储一个部分总和数组,其中 S[i] = 元素 0->i 的总和,因此您的答案将是 S[B] - S[A-1]...
  • 所以不是让其他人为您解决编程难题的服务。

标签: c++ algorithm vector time-complexity big-o


【解决方案1】:

如果允许预处理,可以使用辅助数组来完成。

第二个数组的每个元素将包含相应元素和所有前面元素的总和。这种一次性预处理是 O(n) 时间和 O(n) 空间。

例如:

int Vsum[7];
Vsum[0] = V[0];
for (int i=1; i<7; i++) {
    Vsum[i] = Vsum[i-1] + V[i];
}

因此,对于您给定的数组,相应的求和数组 Vsum 将包含:

{0, 1, 3, 3, 7, 7, 10}

一旦你有了这个,你只需要执行 2 次查找:一次查找上限,一次查找下限。所以经过预处理,每次执行得到的范围和都是O(1)。

对于 A==2 和 B==6 的示例,您将计算 Vsum[B-1] - Vsum[A] == 7 - 3 == 4

【讨论】:

    【解决方案2】:

    O(1) 空间:没问题。但是“随机”数字总是需要 O(n) 时间。

    【讨论】:

    • 这应该是评论来吧
    • OP 没有指定他正在寻找什么样的 O(1)。我相信我的帖子回答了这个问题?
    • 这个问题不值得实际回答
    • @Treycos FIne 如果您认为这个问题很愚蠢并且不值得回答。那你为什么不直接忽略它呢?因为你不喜欢这个问题而对答案投反对票是否有意义?在我看来,OP 似乎还没有掌握大 O 符号的含义,并且需要考虑空间和时间复杂度。我的回答是试图明确这些都是 big-O 的一部分,并且如果做得好,具体示例确实具有 O(1) 的两个复杂性之一。
    • 阅读以上内容,这是一个答案,而不是评论,它的解释和写得很好
    猜你喜欢
    • 1970-01-01
    • 2022-01-22
    • 1970-01-01
    • 2012-03-04
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-11-01
    • 1970-01-01
    相关资源
    最近更新 更多