C#serial For - >并行For:结果混乱

时间:2013-08-28 09:56:06

标签: c# multithreading parallel-processing

这可能是一个基本的问题(我必须承认,我对并行编程不是很有经验)。

我编写了一个单线程C#程序,在此期间创建了一个参数数组p,然后使用函数p[i]评估每个参数f,并( p[i], f( p[i] ) )class Agent { private double[] parameter; private double value; public Agent( double[] par, double val ) { this.parameter = par; this.val = value; } } class Work { public void optimise() { // return an array of parameters, each one of which is a double array itself double[][] parameter = getParameters(); Agent[] results = new Agent[ parameter.Length ]; for ( int idx = 0; idx < parameter.Length; idx++ ) results[ idx ] = new Agent( parameter[idx], cost_function( parameter[ idx ] ) ); } private double cost_function( double[] par ) { // evaluate par, get result return result; } } 然后将每个评估的1}放入Heap(按功能值排序)。非常粗略,它看起来像这样:

cost_function

由于parameter的评估相当冗长,而且parameter很长,所以我考虑将其并行化,将Parallel.For的内容分成段,然后使用{{1}在每个细分上。相当天真,我将例程optimise改为:

  public void optimise() {

    // select an appropriate number of threads, e.g.
    int number_of_threads = Environment.ProcessorCount;

    // return an array of parameters, each one of which is a double array itself
    double[][] parameter = getParameters();

    // split the array of parameters into #number_of_threads many 
    // segments (of roughly equal size)
    double[][][] par_segments = distribute_parameter( parameter );

    Agent[][] results = new Agent[ number_of_threads ];


    // process each segment in an individual thread
    Parallel.For( 0, number_of_threads, idx => {

      results[ idx ] = new Agent[ par_segments[ idx ].Length ];
      for ( int agent = 0; agent < par_segments[ idx ].Length; agent++ )
        results[ idx ][ agent ] = 
          new Agent( par_segments[ idx ][ agent ], cost_function( par_segments[ idx ][ agent ] );
    } );
  }

我天真的期望是,对于每个片段(即每个idx),内部将被一致地处理,特别是在每个new Agent( p, cost_function( p ) )的创建中,两个{{ 1}}在那个表达式中是相同的,并且结果p确实包含一对相应的参数和函数值。但我得到的是Agent,我甚至不认为new Agent( p1, cost_function( p2 ) )是原始p2数组的一部分。

如果我锁定其中的最后一个语句,parameter例程工作正常,但当然这会使并行化无用。 有没有更好的方法来确保结果矩阵将填充一致的参数/值对,而不需要更改原始的Parallel.For例程?

如果是这样,是否有一个很好的在线资源可以解释这一点?最后一个问题:关于这个主题的什么是好书?

提前致谢! 最好的,罗布

1 个答案:

答案 0 :(得分:0)

没有完整的代码就很难掌握它,但我认为你的意思是这样的:

var result = from parameter in parameters.AsParallel()
             select new Agent(parameter, cost_function( parameter));