Browse Source

localInit is now called once per thread rather than once per Parallel call

Signed-off-by: Marcus Cuda <marcus@cuda.net>
la-knuth
Marcus Cuda 17 years ago
parent
commit
4e9ed41576
  1. 40
      src/Numerics/Threading/Parallel.cs
  2. 2
      src/Numerics/Threading/TaskOfT.cs

40
src/Numerics/Threading/Parallel.cs

@ -139,19 +139,31 @@ namespace MathNet.Numerics.Threading
var tasks = new Task<T>[ThreadQueue.ThreadCount];
var size = count / tasks.Length;
var intial = localInit();
// fast forward execution if it's only one or none items
if (count <= 1)
{
if (count == 1)
{
localFinally(body(fromInclusive, intial));
localFinally(body(fromInclusive, localInit()));
}
return;
}
// fast forward execution in case parallelization is disabled
if (Control.DisableParallelization
|| ThreadQueue.ThreadCount <= 1
|| ThreadQueue.IsInWorkerThread)
{
var localresult = localInit();
for (var i = fromInclusive; i < toExclusive; i++)
{
localresult = body(i, localresult);
}
localFinally(localresult);
return;
}
// partition the jobs into separate sets for each but the last worked thread
for (var i = 0; i < tasks.Length - 1; i++)
{
@ -160,15 +172,15 @@ namespace MathNet.Numerics.Threading
tasks[i] = new Task<T>(
localData =>
{
var localresult = localData;
var localresult = (T)localData;
for (var j = start; j < stop; j++)
{
localresult = body(j, (T)localresult);
localresult = body(j, localresult);
}
return (T)localresult;
},
intial);
return localresult;
},
localInit());
ThreadQueue.Enqueue(tasks[i]);
}
@ -176,15 +188,15 @@ namespace MathNet.Numerics.Threading
tasks[tasks.Length - 1] = new Task<T>(
localData =>
{
var localresult = localData;
var localresult = (T)localData;
for (var i = fromInclusive + ((tasks.Length - 1) * size); i < toExclusive; i++)
{
localresult = body(i, (T)localresult);
localresult = body(i, localresult);
}
return (T)localresult;
return localresult;
},
intial);
localInit());
ThreadQueue.Enqueue(tasks[tasks.Length - 1]);
if (tasks.Length <= 0)
@ -316,8 +328,6 @@ namespace MathNet.Numerics.Threading
var maxBlockSize = IntialBlockSize;
var tasks = new List<Task<TLocal>>();
var intial = localInit();
var enumerator = source.GetEnumerator();
while (enumerator.MoveNext())
{
@ -343,7 +353,7 @@ namespace MathNet.Numerics.Threading
return (TLocal)localresult;
},
intial);
localInit());
ThreadQueue.Enqueue(task);
tasks.Add(task);

2
src/Numerics/Threading/TaskOfT.cs

@ -42,7 +42,7 @@ namespace MathNet.Numerics.Threading
private readonly Func<object, TResult> _body;
/// <summary>
/// Variable used to hold state information between interations.
/// Variable used to hold state information between iterations.
/// </summary>
private readonly object _state;

Loading…
Cancel
Save