使用较少的比较查找最大值2d数组N * N.

时间:2016-03-25 15:32:04

标签: algorithm multidimensional-array

我想在C中找到二维数组N * N的最大值,并且比较较少。我只能用O(N ^ 2)算法来做,但我觉得它太慢了。

所以,我想到了另一种方式。我只需循环一次,同时按行和列搜索,并尝试降低复杂性。 (我猜O(2(n-1)))你可以在这张照片中看到我想要做的事情。

Table

我使用相同的循环来检查列和行的内容。

我想知道的是有什么更快的吗?比如对具有O(N log N)复杂度的2D数组进行排序?假设值未排序。

4 个答案:

答案 0 :(得分:4)

如果M x M元素的2d数组没有以任何方式排序,那么你不会比O(M ^ 2)做得更好。

请记住,矩阵具有M ^ 2个元素,因此对它们进行排序将具有O(M ^ 2 log M ^ 2)的复杂度,因为大多数类似的排序是O(N log N)并且这里N = M ^ 2。

答案 1 :(得分:3)

将其划分为[no,of cores]块。获得最大值每个块的并行。从结果中挑选骨骼。

答案 2 :(得分:1)

你可能只是将数组转换为1D数组并遍历扁平指针...

我将解释:

您可能知道,内存中的2D数组以平面状态存储。数组char c[4][2]如下所示:

 | c[0][0] | | c[0][1] | | c[1][0] | | c[1][1] | | c[2][0] | ...
 | Byte 1  | | Byte 2  | | Byte 3  | | Byte 4  | | Byte 5  | ...

在此示例中,c[1][1] == ((char*)c)[3]

因此,当所有成员属于同一类型时,可以安全地将2D数组转换为1D数组,即

 int my_array[20][20];

 for (int i = 0; i < 400 ; i++) {
    ((int *)(my_array))[i] = i;
 }

 // my_array[19][0] == 180;

正如dbush指出的那样(向上投票他的回答),如果你的矩阵是M×M个元素,那么M ^ 2是你最好得到的并且扁平化数组这样简单地避免你复制任何操作之前的记忆。

修改

有人问为什么将数组转换为1D数组可能会更好。

这个想法是避免嵌套的内部循环,使优化器的工作更容易。如果编译器更有可能展开循环,如果它只是单个维度循环并且数组的大小是固定的。

答案 3 :(得分:0)

dbush在复杂性方面肯定有正确的答案。

还应该注意的是,如果你想要更快&#34;就实际运行时间而言(不仅仅是复杂性),您需要考虑缓存。并行下行和列对于数据局部性来说是非常糟糕的,如果您的数据具有相对较大的行,则在向下迭代列时会导致高速缓存未命中。您必须至少触摸一次每个元素才能找到最大值,并且在&#34; row major&#34;中触摸它们将是最快的。排序