所有数组元素的比较 - C算法

时间:2013-03-28 12:21:58

标签: c arrays algorithm matrix comparison

我有一个矩阵 m * n ,对于每一行,我需要比较它们之间的所有元素。 对于我发现的每对情侣,我将调用一个将执行某些计算的函数。

示例:

my_array -> {1, 2, 3, 4, 5, ...}

I take 1 and I have: (1,2)(1,3)(1,4)(1,5)
I take 2 and I have: (2,1)(2,3)(2,4)(2,5)
and so on

使用C我写了这个:

for (i=0; i<array_length; i++) {
    for (k=0; k<array_length; k++) {
        if (i==k) continue;

           //Do something
        }
    }
}

我想知道我是否可以使用复杂度较低的算法。

3 个答案:

答案 0 :(得分:4)

不,根据定义它是O(n ^ 2)[这里解释太久了,但请相信我( - :]
但是你可以减少一半的迭代次数:

for (i=0; i<array_length; i++) {
    for (k=i+1; k<array_length; k++) { // <-- no need to check the values before "i"
           //Do something
           //If the order of i and k make a different then here you should:
           //'Do something' for (i,k) and 'Do something' for (k,i)
        }
    }
}

答案 1 :(得分:3)

您可能会做一些事情,但这些事情是可能的,并且不依赖于阵列性质和您应用的公式。总体复杂性可能会保持不变甚至增长,即使计算速度更快,除非公式的复杂性依赖于其参数,在这种情况下,复杂性的降低可能是可以实现的。

此外,从AO(N ^ a)到BO(N ^ b),其中b>如果B远小于A,那么对于某些N范围,(更高的复杂度)仍然值得追求。

没有特别的顺序:

  • 如果矩阵有多个重复项,则可以方便地使用缓存功能:

    结果函数(arg1,arg2){     int i = index(arg1,arg2); //取决于值,它可能是                                //类似于arg1 *(MAX_ARG2 + 1)+ arg2;     if(!stored [i]){//存储并分配和初始化值                                //在其他地方 - 或在此函数中使用                                //静态标志         stored [i] = 1;         values [i] = true_function(arg1,arg2);     }     返回值[i]; }

    然后,你的内存开销与不同夫妻的数量成正比 可用的值。调用开销可以是O(| arg1 | * | arg2 |),但在某些情况下 (例如true_function()价格昂贵)节省的费用将抵消增加的复杂性。

    • 将公式分成几部分(每个公式都不可能)并将其表达为:

      F(x,y)= G(x)op H(y)op J(x,y)

    然后,你可以做一个O(max(M,N))周期预先计算G []和H []。这也具有O(M + N)存储器成本。只有当F和J之间的计算支出差异显着时才是方便的。或者你可以这样做:

    for (i in 0..N) {
        g = G(array[i]);
        for (j in 0..N) {
            if (i != j) {
                result = f(array[i], array[j], g);
            }
        }
    }
    

    的一些复杂性从O(N ^ 2)下降到O(N)。

    • 如果G()或H()可用于缓存(参数范围有限,功能昂贵),前两种技术可以串联使用。

    • 找到将F(a,b)与F(a + c,b + d)联系起来的“法则”。然后,您可以更有效地运行缓存算法,重用相同的计算。这将一些复杂度从O(N ^ 2)转移到O(N)或甚至O(log N),因此虽然总成本仍然是二次的,但它的增长要慢得多,并且N的更高界限变得切实可行。如果F本身具有比(a,b)中的常数更高的复杂度,则这也可以减少这种顺序(作为一个极端的例子,假设F在a和/或b中迭代)。

答案 2 :(得分:2)

不,如果您包含数组内容的知识,以及优化算法的操作语义,则只能降低计算复杂度。