【发布时间】:2015-09-16 16:48:39
【问题描述】:
我有以下代码:
const int MAX = 101;
const int MIN_COMBINATORIC = 1000000;
int[,] pascalTriangle = new int[MAX, MAX];
Parallel.For(0, MAX, i =>
{
pascalTriangle[i, 0] = 1;
pascalTriangle[i, i] = 1;
});
int counter = 0;
Parallel.For(0, MAX, x => Parallel.For(1, x, y =>
{
int value = pascalTriangle[x - 1, y] + pascalTriangle[x - 1, y - 1];
Interlocked.Exchange(ref pascalTriangle[x, y], value < MIN_COMBINATORIC ? value : MIN_COMBINATORIC);
if(value > MIN_COMBINATORIC)
Interlocked.Increment(ref counter);
}));
Console.WriteLine("Result: {0}", counter);
问题在于它有时会打印出正确答案 (Result: 4075),但有时会打印出随机(且错误)的答案,例如:
Result: 2076Result: 1771Result: 0
我猜这与我在多个线程之间读取和写入共享数组的事实有关。
如您所见,我尝试添加Interlocked.Exhange() 用于线程安全的写操作,但我找不到类似的读取方法(有一个Interlocked.Read() 但它只能读取long 变量)
如何使上述代码以线程安全的方式并发运行?
【问题讨论】:
-
可以通过使用一些同步原语使其成为线程安全的,但我不确定它是否会起作用,因为它似乎依赖于并行运行时可能不完整的先前计算。
标签: c# multithreading concurrency thread-safety task-parallel-library