Комментарии 12
А кто и зачем создает таски через new?
И дедлока тут нет.
Дополню сам себя - вся литература по TPL явно объясняет, какие варианты работы с тасками есть. И да, не обязательно делать Task.Run, можно делать task.Start(), хоть я такого кода за годы работы и не видел.
Как минимум можно почитать MSDN: https://learn.microsoft.com/ru-ru/dotnet/standard/parallel-programming/task-based-asynchronous-programming#creating-and-running-tasks-explicitly
Про Task.Start хотя да он есть, но не удобный в сравнении с Task.Run
Видел несколько раз как упускают этот момент при создании таски и советы как решить это обходным путем. Одно из последних - эта статья.
Разобраться раз и навсегда: Task.WhenAll или Parallel.ForEachAsync в C# / Хабр (habr.com)
Я только учусь писать статьи и решил выложить эту мелочь, но готовиться еще одна - побольше про clikhouse и net channel
Спецов, как погляжу, понаехало - дедлоки увидели, даже трассировок через Environment.CurrentManagedThreadId
нету, и столько выводов делается.
Вот тут тоже, судя по всему, дедлок. Без лишних Producer-Consumer-ских прикрас :))
//АТАТА!! Тут дедлок - таски не запущены, но у нас все равно дедлок!!! await TestTaskConstructors(); async Task TestTaskConstructors() { var task1 = new Task(() => { Console.WriteLine("Hello world from Task1!"); }); var task2 = new Task(() => { Console.WriteLine("Hello world from Task2!"); }); await Task.WhenAll(task1, task2);
Не надо давать уроков, если нет полного понимания как это работает. Вы только больше хаоса из своей головы вносите.
Отступы съехали
//АТАТА!! Тут дедлок - таски не запущены, но у нас все равно дедлок!!!
await TestTaskConstructors();
async Task TestTaskConstructors() {
var task1 = new Task(() => {
Console.WriteLine("Hello world from Task1!");
});
var task2 = new Task(() => {
Console.WriteLine("Hello world from Task2!");
});
await Task.WhenAll(task1, task2);
}
Я подозреваю, что проблема к каком-то очень нестандартном использовании ConfigureAwait
"потрясающая" идея - хватать потоки из пула там где они не нужны. А они почти никогда не нужны при Async await так как ни Task.delay ни ожидания на портах ввода вывода не требует делать это в отдельных потоках. А вы предлагаете для этого делать отдельные потоки. Шутите что ли?)
Как легко получить deadlock на Task.WhenAll