2016-05-14 16 views
-1

Как я могу остановить задачи в списке, чтобы реализовать еще раз.Список задач как я могу остановить задачу C#

for (f = 0; f < 3; f++) 
{ 
    list1.ForEach(t => t.Start()); 
    list1.ForEach(t => t.Wait()); 

    Task.WaitAll(list1.ToArray()); 

    //here is problem 
    list1.ForEach(t => t.Cancel()); 
} 
+0

Пожалуйста, объясните немного больше. Я не могу понять ваш вопрос. – NineBerry

+0

Мне нужно реализовать этот цикл, но после одного выполнения я получаю сообщение об ошибке «Ошибка « System.Threading.Tasks.Task »не содержит определения для« IsCancellationRequested »и никакого метода расширения« IsCancellationRequested », принимающего первый аргумент тип «System.Threading.Tasks.Task» может быть найден (вам не хватает директивы using или ссылки на сборку?) « – Quicki

ответ

1

Задача не может отменить себя. Из кода, который вы показали, выглядит так, как будто у вас есть список задач. Если после этого вы хотите, чтобы иметь возможность отменить задание, пока ваш код выполняется вы должны создать CancellationTokenSource и передать CancellationToken в конструктор по задаче:

list1.Add(new Task<string>((x) => { return x.ToString(); }, cancelationTokenSource.Token)); 

(В коде выше Я предположил, что задача будет возвращает строку, но она будет работать для любой задачи)

Тогда, если вам нужно отменить задание при использовании функций cancelationTokenSource:.

cancelationTokenSource.Cancel(); 

Это будет прекратить задачу. То, что вы тогда можете сделать в самой задаче, - проверить, отменено ли это:

list1.ForEach(t => 
{ 
    if (t.IsCanceled) 
    { 

    } 
} 

Надеюсь, что это поможет. Мой ответ основан на моей интерпретации вашего кода, поскольку в вопросе не было слишком много объяснений. Если вам нужно больше деталей, уточните пожалуйста.

+0

Могу ли я добавить задачу, как здесь? 'Список list1 = новый Список (); для (int i = 0; i <5; i ++) { list1.Add (новая задача (actionA)); } ' – Quicki

+0

На самом деле' cancelationTokenSource.Cancel' не отменяет задачу в способе 'Thread.Abort' - вместо этого она будет останавливать задачу, когда _and if_ задает запрос на ее« CancellationToken », следует ли остановить в следующий раз. Кроме того, задача должна знать его «CancellationToken», передавая его в «Task.Run», просто делает его статус «отмененным» вместо «Failed», если токен выдает «TaskCanceledException» ... – Haukinger

+0

Нет необходимости отменять в этом случае, поскольку все задачи были выполнены из-за вызова WaitAll(); –

0

Пара вещи первой:

Не использовать конструктор задач. Использовать Task.Run() см. http://blogs.msdn.com/b/pfxteam/archive/2010/06/13/10024153.aspx

Но в вашем случае я даже не уверен, что вы должны использовать задачи вообще. Для циклов есть PLINQ.

этот кусок кода внутри цикла

list1.ForEach(t => t.Start()); 
list1.ForEach(t => t.Wait()); 

в основном делает его запустить запустить задачу, а затем ждать его перед началом следующего цикла.

Я предлагаю использовать Parallel.ForAll(), когда вам нужно выполнить несколько операций с ЦПУ в цикле. Если это привязка IO, используйте async/await

Затем вы пытаетесь отменить задания после того, как их дождались. Это не имеет смысла, или я недостаточно понимаю, чего вы хотите достичь.

Теперь давайте поговорим об отмене работы. Вам нужно что-то вроде этого:

var cts = new CancellationTokenSource(); 
var ct = cts.Token; 

Предоставьте CancellationToken ct задачам в списке1. Затем вызовите cts.Cancel(), чтобы отменить все задачи, которым задан токен. Например, Task.Run(asyncWork, ct), где asyncWork - это действие, которое вы хотите выполнить.

В asyncWork действий, проверьте отмены с использованием ct.ThrowIfCancellationRequested();

См https://blogs.msdn.microsoft.com/andrewarnottms/2014/03/19/recommended-patterns-for-cancellationtoken/

Вы должны предоставить больше о задачах, поставленных в list1 для лучшего совета.

Смежные вопросы