public static void StaticWorkerFor(ParallelTasksStaticWorkerForInput input) { if (input.TasksLow < 0 || input.TasksHigh < input.TasksLow) return; ModuleProc PROC = new ModuleProc("ParallelTasks", "StaticFor"); if (input.WorkerCount <= 0) { if (input.Chunk > 0) { input.WorkerCount = (int)Math.Max(Math.Ceiling(Convert.ToDouble(input.TasksHigh) / Convert.ToDouble(input.Chunk)), 1); } else { input.WorkerCount = 1; } } if (input.Chunk <= 0) { input.Chunk = (input.TasksHigh / input.WorkerCount); } if (input.Chunk <= 0) input.Chunk = 1; if (input.TasksHigh < input.Chunk) input.Chunk = ((input.TasksHigh - input.TasksLow) / input.WorkerCount); CountdownEvent cde = new CountdownEvent(input.WorkerCount); Thread[] threads = new Thread[input.WorkerCount]; int currentCount = 0; ParallelTaskOptions options = new ParallelTaskOptions(); WorkerItem item = new WorkerItem() { ExecutorService = input.Executor, Result = new ParallelTaskResult(ParallelTaskResultStatus.Created), Completed = input.WorkCompleted, EventHandle = cde, }; try { for (int i = 0; i < input.WorkerCount; i++) { threads[i] = Extensions.CreateThreadAndStart((o) => { int k = (int)o; int start = input.TasksLow + (k * input.Chunk); int end = ((k == (input.WorkerCount - 1)) ? input.TasksHigh : (start + input.Chunk)); // work input.Chunk started if (input.WorkChunkStarted != null) { try { input.WorkChunkStarted(new ParallelTaskWorkChunkStartArgs() { Options = options, ThreadIndex = i, ChunkStart = start, ChunkEnd = end, SeqStart = 0, SeqEnd = (end - 1 - start), }); } catch (Exception ex) { Log.Exception(PROC, ex); item.Result.Exceptions.Add(ex); } } // work int chunkProgress = start; for (int j = start, sj = 0; j < end; j++, sj++) { if ((input.Executor != null && input.Executor.IsShutdown) || options.IsCancelled) break; chunkProgress = j; try { int proIdx = Interlocked.Increment(ref currentCount); int proPerc = (int)(((float)proIdx / (float)input.TasksHigh) * 100.0); string text = string.Format("{0:D} of {1:D} ({2:D} %)", proIdx, input.TasksHigh, proPerc); input.Work(new ParallelTaskWorkArgs() { Options = options, ThreadIndex = k, ChunkProgress = j, ChunkSeqProgress = sj, OverallProgress = proIdx, Total = input.TasksHigh, ProgressText = text, }); } catch (Exception ex) { Log.Exception(PROC, ex); item.Result.Exceptions.Add(ex); } finally { Interlocked.Increment(ref currentCount); } Thread.Sleep(input.SleepInMilliseconds); } // work input.Chunk completed if (input.WorkChunkCompleted != null) { try { input.WorkChunkCompleted(new ParallelTaskWorkChunkCompletedArgs() { Options = options, ThreadIndex = i, ChunkProgress = chunkProgress, OverallProgress = currentCount, }); } catch (Exception ex) { Log.Exception(PROC, ex); item.Result.Exceptions.Add(ex); } } cde.Signal(); }, i, "StaticFor_" + i.ToString() + "_"); Thread.Sleep(10); } } catch (Exception ex) { Log.Exception(PROC, ex); } finally { Extensions.CreateThreadAndStart((o) => { WorkerItem wi = o as WorkerItem; wi.EventHandle.Wait(); wi.Result.Status = (((input.Executor != null && input.Executor.IsShutdown) || options.IsCancelled) ? ParallelTaskResultStatus.Canceled : ParallelTaskResultStatus.Completed); if (wi.Completed != null) { wi.Completed(new ParallelTaskWorkCompletedArgs() { Result = wi.Result, }); } }, item, "StaticFor_Wait_"); } }
public static void StaticWorkerFor(ParallelTasksStaticWorkerForInput input) { if (input.TasksLow < 0 || input.TasksHigh < input.TasksLow) { return; } ModuleProc PROC = new ModuleProc("ParallelTasks", "StaticFor"); if (input.WorkerCount <= 0) { if (input.Chunk > 0) { input.WorkerCount = (int)Math.Max(Math.Ceiling(Convert.ToDouble(input.TasksHigh) / Convert.ToDouble(input.Chunk)), 1); } else { input.WorkerCount = 1; } } if (input.Chunk <= 0) { input.Chunk = (input.TasksHigh / input.WorkerCount); } if (input.Chunk <= 0) { input.Chunk = 1; } if (input.TasksHigh < input.Chunk) { input.Chunk = ((input.TasksHigh - input.TasksLow) / input.WorkerCount); } CountdownEvent cde = new CountdownEvent(input.WorkerCount); Thread[] threads = new Thread[input.WorkerCount]; int currentCount = 0; ParallelTaskOptions options = new ParallelTaskOptions(); WorkerItem item = new WorkerItem() { ExecutorService = input.Executor, Result = new ParallelTaskResult(ParallelTaskResultStatus.Created), Completed = input.WorkCompleted, EventHandle = cde, }; try { for (int i = 0; i < input.WorkerCount; i++) { threads[i] = Extensions.CreateThreadAndStart((o) => { int k = (int)o; int start = input.TasksLow + (k * input.Chunk); int end = ((k == (input.WorkerCount - 1)) ? input.TasksHigh : (start + input.Chunk)); // work input.Chunk started if (input.WorkChunkStarted != null) { try { input.WorkChunkStarted(new ParallelTaskWorkChunkStartArgs() { Options = options, ThreadIndex = i, ChunkStart = start, ChunkEnd = end, SeqStart = 0, SeqEnd = (end - 1 - start), }); } catch (Exception ex) { Log.Exception(PROC, ex); item.Result.Exceptions.Add(ex); } } // work int chunkProgress = start; for (int j = start, sj = 0; j < end; j++, sj++) { if ((input.Executor != null && input.Executor.IsShutdown) || options.IsCancelled) { break; } chunkProgress = j; try { int proIdx = Interlocked.Increment(ref currentCount); int proPerc = (int)(((float)proIdx / (float)input.TasksHigh) * 100.0); string text = string.Format("{0:D} of {1:D} ({2:D} %)", proIdx, input.TasksHigh, proPerc); input.Work(new ParallelTaskWorkArgs() { Options = options, ThreadIndex = k, ChunkProgress = j, ChunkSeqProgress = sj, OverallProgress = proIdx, Total = input.TasksHigh, ProgressText = text, }); } catch (Exception ex) { Log.Exception(PROC, ex); item.Result.Exceptions.Add(ex); } finally { Interlocked.Increment(ref currentCount); } Thread.Sleep(input.SleepInMilliseconds); } // work input.Chunk completed if (input.WorkChunkCompleted != null) { try { input.WorkChunkCompleted(new ParallelTaskWorkChunkCompletedArgs() { Options = options, ThreadIndex = i, ChunkProgress = chunkProgress, OverallProgress = currentCount, }); } catch (Exception ex) { Log.Exception(PROC, ex); item.Result.Exceptions.Add(ex); } } cde.Signal(); }, i, "StaticFor_" + i.ToString() + "_"); Thread.Sleep(10); } } catch (Exception ex) { Log.Exception(PROC, ex); } finally { Extensions.CreateThreadAndStart((o) => { WorkerItem wi = o as WorkerItem; wi.EventHandle.Wait(); wi.Result.Status = (((input.Executor != null && input.Executor.IsShutdown) || options.IsCancelled) ? ParallelTaskResultStatus.Canceled : ParallelTaskResultStatus.Completed); if (wi.Completed != null) { wi.Completed(new ParallelTaskWorkCompletedArgs() { Result = wi.Result, }); } }, item, "StaticFor_Wait_"); } }