Sobes.tech
Middle

Jak zrušit provádění úkolu (task) v C#?

sobes.tech AI

Odpověď od AI

Pro zrušení úkolu v C# se používá mechanismus CancellationToken a CancellationTokenSource.

  1. Vytvoří se CancellationTokenSource.
  2. Z CancellationTokenSource se získá CancellationToken.
  3. CancellationToken se předá do metody, která úkol vykonává.
  4. Uvnitř vykonávané metody se periodicky kontroluje vlastnost IsCancellationRequested tokenu.
  5. Pokud je IsCancellationRequested rovno true, generuje se OperationCanceledException nebo se provádí jiná logika ukončení práce.
  6. Pro požadavek na zrušení se volá metoda Cancel() u objektu CancellationTokenSource.

Příklad použití:

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

// Vytvoření zdroje tokenů zrušení
CancellationTokenSource cts = new CancellationTokenSource();
CancellationToken token = cts.Token;

// Vytvoření úkolu
Task task = Task.Run(() =>
{
    try
    {
        for (int i = 0; i < 100; i++)
        {
            // Kontrola, zda bylo požádáno o zrušení
            if (token.IsCancellationRequested)
            {
                // Vyvolání výjimky OperationCanceledException
                token.ThrowIfCancellationRequested();
            }

            // Simulace práce
            Console.WriteLine($"Pracuji... {i}");
            Thread.Sleep(100);
        }
    }
    catch (OperationCanceledException)
    {
        // Zpracování výjimky zrušení
        Console.WriteLine("Úkol byl zrušen.");
    }
    catch (Exception ex)
    {
        // Zpracování jiných výjimek
        Console.WriteLine($"Došlo k chybě: {ex.Message}");
    }
}, token); // Předání tokenu do úkolu

// Čekání určitou dobu, poté požadavek na zrušení
Thread.Sleep(500);
Console.WriteLine("Požadavek na zrušení...");
cts.Cancel();

// Čekání na dokončení úkolu
try
{
    task.Wait();
}
catch (AggregateException ae)
{
    // Zpracování výjimek, včetně OperationCanceledException
    foreach (var e in ae.InnerExceptions)
    {
        if (e is OperationCanceledException)
        {
            Console.WriteLine("Dokončený zrušený úkol (přes Wait).");
        }
        else
        {
            // Zpracování jiných výjimek
            Console.WriteLine($"Chyba při ukončení úkolu: {e.Message}");
        }
    }
}

Console.WriteLine("Hlavní program byl ukončen.");

Alternativy:

  • Vrácení speciální hodnoty nebo příznaku z úkolu.
  • Kontrola příznaku nastaveného zvenčí bez použití CancellationToken.

Nicméně, CancellationToken je standardní a doporučený přístup díky své integraci s Task Parallel Library (TPL), asynchronními operacemi a podporou OperationCanceledException.