Task.Start (), Task.Run () ve Task.Factory.StartNew () kullanımı ile ilgili


143

Aynı işi yapan TPL kullanımı ile ilgili 3 rutin gördüm; İşte kod:

public static void Main()
{
    Thread.CurrentThread.Name = "Main";

    // Create a task and supply a user delegate by using a lambda expression. 
    Task taskA = new Task( () => Console.WriteLine("Hello from taskA."));
    // Start the task.
    taskA.Start();

    // Output a message from the calling thread.
    Console.WriteLine("Hello from thread '{0}'.", 
                  Thread.CurrentThread.Name);
    taskA.Wait();
}

public static void Main()
{
    Thread.CurrentThread.Name = "Main";

    // Define and run the task.
    Task taskA = Task.Run( () => Console.WriteLine("Hello from taskA."));

    // Output a message from the calling thread.
    Console.WriteLine("Hello from thread '{0}'.", 
                      Thread.CurrentThread.Name);
    taskA.Wait();
}

public static void Main()
{
    Thread.CurrentThread.Name = "Main";

    // Better: Create and start the task in one operation. 
    Task taskA = Task.Factory.StartNew(() => Console.WriteLine("Hello from taskA."));

    // Output a message from the calling thread.
    Console.WriteLine("Hello from thread '{0}'.", 
                    Thread.CurrentThread.Name);

    taskA.Wait();                  
}

Sadece MS aynı VUK içinde çünkü onlar tüm çalışmaları işlerini çalıştırmak için 3 farklı yöntem sunar neden anlamıyorum: Task.Start(), Task.Run()ve Task.Factory.StartNew().

Beni, edilir Söyle Task.Start(), Task.Run()ve Task.Factory.StartNew()hepsi aynı amaçla kullanılabilir veya farklı bir öneme var?

Ne zaman Task.Start(), ne zaman Task.Run()ve ne zaman kullanılmalı Task.Factory.StartNew()?

Lütfen senaryolara göre gerçek kullanımlarını örneklerle çok ayrıntılı olarak anlamama yardımcı olun, teşekkürler.


bir var burada açıklayan eski yazı ve yeni buradaTask.Run - belki bu soruya cevap olacak;)
Carsten

İşteTask.Start aslında yararlı olduğu bir örnek .
noseratio

Yanıtlar:


171

Task.RunTask.Factory.StartNewbelirli güvenli argümanlarla ilgili bir kısayoldur :

Task.Factory.StartNew(
    action, 
    CancellationToken.None, 
    TaskCreationOptions.DenyChildAttach, 
    TaskScheduler.Default);

.Net 4.5 'e giderek artan sıklıkta asyncve boşaltma çalışmalarına yardımcı olmak için eklenmiştir ThreadPool.

Task.Factory.StartNew(.Net 4.0'da TPL ile birlikte eklenmiştir) çok daha sağlamdır. Sadece Task.Runyeterli değilse, örneğin kullanmak istediğinizde kullanmalısınız TaskCreationOptions.LongRunning(delege eşzamansız olduğunda gereksizdir. Blogumda daha fazlası: LongRunning Görev için Yararsızdır . Async-await ile çalıştırın ). Daha üzerinde Task.Factory.StartNewde Task.Run Task.Factory.StartNew vs

Bunu yapmak için son derece iyi bir neden bulamadığınız sürece asla bir Taskarama ve çağrı Start()yapmayın. Yalnızca görevler oluşturmanız gereken bir parçanız varsa, ancak bunları zamanlama ve oluşturmadan zamanlayan başka bir parçanız varsa kullanılmalıdır. Bu neredeyse hiç uygun bir çözüm değildir ve tehlikeli olabilir. Daha vs "Task.Factory.StartNew" "Yeni Görev (...). Başlat"

Sonuç olarak, çoğunlukla kullanın Task.Run, kullanmanız Task.Factory.StartNewve asla kullanmamanız durumunda kullanın Start.


5
u "Asla bir Görev oluşturmayın ve Start () çağırın", beni Task.Start () öğesinin neden olabileceğini gösterecek iyi bir yazıya yönlendirin. detaylar gerekir çünkü ur önlemek için söyleyerek. Cevap için teşekkürler.
Mou

bu bağlantı hakkında konuşmak ru blogs.msdn.com/b/pfxteam/archive/2010/06/13/10024153.aspx ??
Mou

1
@ Task.StartÇoğunlukla türleri miras almak için yeri var.
Yuval Itzchakov

1
@Mou Sadece bir kez çağrıldığından emin olmak için senkronizasyon gerektirdiği için verimsiz. Diğer seçenekler yoktur.
i3arnon


2

Kısa cevap :

Yuvalanmış çocukların görevlerini kullanmıyorsanız ve görevlerinizin her zaman Thread Pool'da yürütülmesini istiyorsanız, kullanmak daha iyidir Task.Run.

Uzun cevap:

Task.Runve Task.Factory.StartNewher iki oluşturmak için destek sağlar ve biz oluşturmanıza gerek kalmaz zamanlama Görev nesneleri Taskve çağrıStart()

Task.Run(action);

Şuna eşittir:

Task.Factory.StartNew(action, CancellationToken.None, TaskCreationOptions.DenyChildAttach, TaskScheduler.Default);

Ve

Task.Factory.StartNew(action);

Şuna eşittir:

Task.Factory.StartNew(action, CancellationToken.None, TaskCreationOptions.None, TaskScheduler.Current);

Task.Runkullanır TaskCreationOptions.DenyChildAttach; bu, çocukların görevlerinin üst öğeye TaskScheduler.Defaulteklenemeyeceği anlamına gelir ve bu da İş parçacığı Havuzu'nda görevleri çalıştıran görevlerin her zaman görevleri çalıştırmak için kullanılacağı anlamına gelir.

Task.Factory.StartNewkullanımları TaskScheduler.Currentgeçerli iş parçacığının zamanlayıcı demektir, bu olabilir TaskScheduler.Defaultama her zaman değil.

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.