1

如何并行化聚合多个双精度的循环?

可以将其作为两个或多个Parallel.For循环执行,其中对单个双精度求和,但是,在我的情况下,这将需要重复两个变量共有的昂贵函数。

单线程形式的简化示例:

static void Main()
{
    double sum1 = 0.0;
    double sum2 = 0.0;
    for (int i = 2; i < 10; i++)
    {
        double result = function1(i);
        sum1 += result;
        sum2 += function2(result);
    }
    Console.WriteLine(sum1 + " " + sum2);
    Console.ReadLine();
}

private static double function1(int x)
{
    return Math.Exp((double)x);
}

private static double function2(double x)
{
    return Math.Pow(x, 2);
}

这里的函数 1 和 2 实际上非常昂贵,因此只能评估一次。

我发现用于聚合一个双精度的代码:

        object lockObject = new object();
        double sum = 0.0d;

        Parallel.For(0, 10,
            () => 0.0d,

            (x, loopState, partialResult) =>
            {
               return (double)x / 100.0 + partialResult;
            },

            (localPartialSum) =>
            {
               lock (lockObject)
               {
                 sum += localPartialSum;
               }
            });
4

1 回答 1

1

您可以使用Parallel.For线程本地数据:

object sync = new object();
double sum1 = 0.0;
double sum2 = 0.0;
Parallel.For<Tuple<double, double>>(2, 10,
    () => { return new Tuple<double, int>(0.0, 0.0); },
    (i, pls, state) =>
    {
        double result = function1(i);
        state = new Tuple<double, double>( state.Item1 + result, state.Item2 + function2(result))
        return state;
    },
    state => { lock (sync) { sum1 += state.Item1; sum2 += state.Item2; } }
);

如果您使用包含两个doubles 而不是 s的可变类Tuple,则可以稍微简化代码。

于 2013-01-30T10:53:40.647 回答