.Net Task class

Cette classe, comme son nom l’indique, permet au développeur d’exécuter un travail synchrone ou asynchrone dans un thread séparé. Elle offre pas mal d’avantages par rapport aux autres classes bien connues comme le BackgroundWorker comme la possibilité d’annuler une tâche, la possibilité de créer des sous-tâches sous forme arborescente, la possibilité de choisir l’enchaînement des tâches, de lancer des tâches en parallel etc. En échange ce que vous retrouverez dans BackgroundWorker et vous ne retrouverez pas dans Task est la possibilité de rapporter le progrès de l’exécution. Heureusement c’est une fonctionnalité qui est assez facilement réalisable en utilisant encore une classe Task. Cliquez ici pour voir une belle implémentation de comment faire cela. Sur ce blog vous pouvez également comparer deux implémentations équivalentes en utilisant Task et BackgroundWorker.

Task se trouve dans le namespace System.Threading.Tasks. Cette classe et les types associés font partie d’un ensemble de types publics appelé TPL (Task Parallel Library). TPL représente un nouveau modèle de programmation introduit par Microsoft dans .Net Framework 4.

Pour plus d’informations je vous invite à aller visiter MSDN sur la page dediée à TPL (Task Parallel Library).

Je ne vais pas insister avec beaucoup d’exemples de code, mais voici un court exemple issue de MSDN qui montre comment instancier et utiliser une seule instance de la classe Task:

using System;
using System.Threading;
using System.Threading.Tasks;

class Program
{
    static void Main()
    {
        //Creation du CancellationToken
        var tokenSource = new CancellationTokenSource();
        CancellationToken ct = tokenSource.Token;

        // Créer et lancer la tâche
        var task = Task.Factory.StartNew(() =>
        {
            // Est-ce que la tâche à déjà été annulée?
            ct.ThrowIfCancellationRequested();

            //do work
            bool moreToDo = true;
            while (moreToDo)
            {
                // On verifie que la tâche n'a pas été annulée
                if (ct.IsCancellationRequested) {
                    // TODO: travaux de netoyage si la tâche est annulée

                    ct.ThrowIfCancellationRequested();
                }
            }
        }, tokenSource.Token); // On transmet le token au StartNew().

        //on annule la tâche on appelant la méthode Cancel() du token
        tokenSource.Cancel();

        // On attends sur le thread courant que la tâche se finisse
        // en utilisant la méthode Wait/WaitAll avec des try-catch:
        try
        {
            task.Wait();
        }
        catch (AggregateException e)
        {
            foreach (var v in e.InnerExceptions)
                Console.WriteLine(e.Message + " " + v.Message);
        }

        Console.ReadKey();
    }
}

L’objet CancellationToken transmis à la méthode StartNew() permet d’annuler la tâche. On aurait pu également utiliser la même instance de CancellationToken pour créer d’autre tâches ou sous-tâches. Danc ce cas l’appel de la méthode Cancel() annule toutes les tâches qui utilisent ce token.

Une dernière chose – la tâche s’intègre plutôt bien avec d’autres API existantes, comme IAsyncResult, AsyncWaitHandle et autres ce qui est particulièrement utile pour l’intégration à des projets existants.

Il est clair que Task est une évolution par rapport à ce qu’on avait et elle devrait rendre la vie du développeur beaucoup plus facile lorsqu’il s’agit de travailler avec une séquence de tâches qui s’exécutent de manière synchrone ou asynchrone, séquentielle ou parallèle, qui peuvent contenir des sous-tâches ou qui doivent supporter la fonction d’annulation.

Laisser un commentaire

Votre adresse de messagerie ne sera pas publiée. Les champs obligatoires sont indiqués avec *