gpt4 book ai didi

arrays - 在大小为 N 的数组的每 k 个元素中查找最小和第二小的元素

转载 作者:塔克拉玛干 更新时间:2023-11-03 05:02:24 24 4
gpt4 key购买 nike

我试图在 N 大小的数组的 k 个元素中找到最小和次小的元素(没有排序和最小/最大堆)。

使用传统的方法,首先从第 0 个元素开始,在前 k 个元素中找到最小和第二小的元素,然后将起点移动 1 并重复该过程。但是它的复杂度是O(Nk)。如果可能,我需要一个复杂度为 O(N) 的解决方案。对此有何建议?

在 Jubobs 的评论后编辑:例如如果说数组是 {12, 1, 78, 90, 57, 89, 56} 并且 k3,那么对于第一个 k 个元素 (12, 1, 78) 最小的元素将是 1,第二小的元素将是 12。对于第二个 k 元素 (1, 78, 90),最小的元素将是 1,第二小的元素将是 78等等。

以下是我用 O(Nk) 复杂度编写的代码片段:

int j=0;
while(j < input.length-k+1) {
int i=j;
for(i=j; i < j+k; i++) {
if(input[i] < min) {
min2 = min;
min = input[i];
} else if(input[i] > min && input[i] < min2) {
min2 = input[i];
}
}
}

最佳答案

您可以使用 deque你保持分类。

在每一步中,如果双端队列中的第一个元素 ( d.front.index ) 早于 k相对于当前步骤的步骤,将其弹出( d.popFront() )。

然后,当数组中当前位置的元素小于双端队列中的最后一个元素(d.back.value)时,从双端队列中弹出元素(d.popBack())。

最后,将当前值添加到双端队列的末尾 ( d.pushBack() )。

在每一步,d.front.value将是 [step - k + 1, step] 的最小值.

您可以将双端队列存储为大小为 k 的链表.然后你将可以随时访问其中的第二个元素,这将是 [step - k + 1, step] 中第二小的元素。 .如果由于弹出每个元素而最终只得到一个元素,则必须小心。在那种情况下,弹出的可能是 future 查询中第二小的。您可以将它们保存在您处理类似于双端队列的另一个列表中,请参见下面的示例。

这是 O(n)摊销,因为数组中的每个元素最多进入和离开双端队列一次。它可能看起来像 O(nk)因为你会有一些嵌套循环,但如果你考虑操作总数,你会发现它实际上是 O(n) .

伪代码

for i = 0, i < n:
if not d.empty and i - d.front.index >= k:
d.popFront()
while not d.empty and d.back.value > a[i]:
d.popBack()

d.pushBack({index = i, value = a[i]})

output d.front.value as the minimum value in [i - k + 1, i]

跟踪第二个最小值的代码留作练习。

以你的例子为例:

a = {12, 1, 78, 90, 57, 89, 56}, k = 3

d = {12}
d = {1} (12 popped, track this)
d = {1, 78} => we have to output smallest and second smallest in [0, 2].
=> smallest is always the first in the deque, so 1
=> second = min(12 [this was popped], 78) = 12
d = {1, 78, 90)
=> smallest 1, second is 78 (12 is too old now)
d = {57}
=> 1 popped for being too old, the others for being too large
=> smallest = 57, second = 78 (last popped)
d = {57, 89}
=> smallest = 57, second = 89
d = {56}
=> smallest = 56, second = 57

基本上,您为第二小的数组保留一个数组。这将包含还不太旧的弹出值。这些也将被排序,但降序排列。

此方法的示例运行,其中 d2是第二个数组:

a = {12, 1, 78, 90, 57, 89, 56} 

d = {12}, d2 = {}
d = {1}, d2 = {12}
d = {1, 78}, d2 = {12}
=> output 1, 12
d = {1, 78, 90}, d2 = {} - 12 was too old
=> output 1, 78
d = {57} d2 = {90, 78}
=> output 57, 78
d = {57, 89} d2 = {90} - 78 too old
=> output 57, 89 (if we had 91 instead of 89, we'd have output the 90 in d2)
d = {56} d2 = {89, 57}
=> output 56, 57

关于arrays - 在大小为 N 的数组的每 k 个元素中查找最小和第二小的元素,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/32425583/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com