关于C ++中函数调用和求值的问题

时间:2011-05-13 11:36:25

标签: c++ arrays function

嘿那里, 关于以下问题我可能有一个直截了当的问题:

我有一个功能

double afunction(double *myarray)
{   
    double ret = 1.0;
    for(int i = 0; i < 4; i++)
        ret *= myarray[i]*myarray[i];
    return ret;
}

现在我想修改它,以便传递两个新参数:int index,描述要更改的myarray索引,如下所示:myarray[ index ] = *add;。这将是以下内容:

double afunction(double *myarray, int index, double *add)
{   
    myarray[ index ] += *add;
    double ret = 1.0;
    for(int i = 0; i < 4; i++)
        ret *= myarray[i]*myarray[i];
    return ret;
}

问题是:我不想修改数组myrray而我不想为此创建新数组因为memory-respect(稍后将在GPU上计算,无论如何我都无法在内核函数中分配一个全新的数组。 轻松解决这个问题? 谢谢!

修改 对不起,我输错了一些东西。相反myarray[ index ] = *add;我想说myarray[ index ] += *add;

EDIT2 更大功能的示例,以后可以轻松扩展到大约50种不同的返回案例。因此,要在每个返回案例中添加myarray[index]来修改特定值*add的if语句非常难看:(

double afunction(double *myarray, int funcIndex, int indexAdd, double *add)
{   
    myarray[ indexAdd ] += *add;

    if(funcIndex >= 1 && funcIndex <= 4)
        return myarray[1]*myarray[1]*myarray[2];

    switch(funcIndex)
    {
        case 5:
            return sin(myarray[3]) * cos(myarray[1]);
        case 6:
            double ret = exp(myarray[1]);
            for(int i = 1; i < 5; i++)
                ret *= (myarray[ i ]-myarray[ 5-i ]);
            return ret;
        case 7:
            double ret = 0.0;
            for(int i = 1; i < 10; i++)
                ret += myarray[ i ];
            return ret;
    }

    return 0.0;
}

3 个答案:

答案 0 :(得分:5)

double ret = 1.0;
for(int i = 0; i < 4; i++)
    if (index == i)
        ret *= (*add) * (*add);
    else
        ret *= myarray[i]*myarray[i];

或:

double ret = (*add) * (*add);
for(int i = 0; i < 4; i++)
    ret *= myarray[i]*myarray[i];

ret /= myarray[index] * myarray[index];

虽然您使用的是浮点数,但它并不是100%等效。

编辑:好的,看到您编辑了原始问题。可以接受的另一种选择是:

myarray[ indexAdd ] -= *add;

完成其余计算后。同样,我无法保证myarray[indexAdd]完全返回旧值。

甚至更好,将旧值保存在函数顶部,然后将其恢复:

float old = myarray[ indexAdd ];
myarray[ indexAdd ] += *add;
//do work
myarray[ indexAdd ] = old;

答案 1 :(得分:4)

double afunction(double *myarray, int index, double *add)
{   
    double ret = (*add) * (*add);
    for(int i = 0; i < 4; i++)
        if( i != index )
            ret *= myarray[i]*myarray[i];
    return ret;
}

答案 2 :(得分:2)

有几种可能的解决方案:

显而易见:

double
aFunction( double* array, int index, double add )
{
    double result = 1.0;
    for ( int i = 0; i != 4; ++ i ) {
        double tmp = array[i];
        if ( i == index ) {
            tmp += add;
        }
        result *= tmp * tmp;
    }
    return result;
}

可能更快(如果在循环中没有),但可能不同 结果:

double
aFunction( double* array, int index, double add )
{
    double result = 1.0;
    for ( int = 0; i != 4; ++ i ) {
        result *= array[i] * array[i];
    }
    //  Since we multiplied by array[i]^2, when we should
    //  have multipied by (array[i] + add)^2...
    result *= 2 * array[index] * add + add * add;
    return result;
}

我怀疑这个是否值得为此而烦恼 四个元素的数组:四个if可能不比它贵 最后的额外计算。但是,对于更长的阵列,它可能是 值得考虑。

最后,更多供参考,因为它真的很丑,而且只适用于 单线程环境:

double
aFunction( double* array, int index, double add )
{
    array[index] += add;
    double result = 1.0;
    for ( int i = 0; i != 4; ++ i ) {
        result *= array[i] * array[i];
    }
    array[index] -= add;
    return result;
}

根据实际的硬件和编译器优化,可以 是最快的。 (但同样,只有四个元素,它远非如此 一定。)

关于代码的另外两条评论:如果你不打算修改 array,您应该将其作为double const*传递给它 消除了上面的最后一种可能性),因为你所做的只是阅读 单个值,将add作为指针传递真的没有意义; 在上面的代码中,我已经按值传递了它。