Maison >développement back-end >C++ >Comment puis-je intercepter les exceptions levées à partir d'un thread distinct dans .NET ?

Comment puis-je intercepter les exceptions levées à partir d'un thread distinct dans .NET ?

Mary-Kate Olsen
Mary-Kate Olsenoriginal
2025-01-06 00:49:39139parcourir

How Can I Catch Exceptions Thrown from a Separate Thread in .NET?

Capturer les exceptions levées dans différents threads : un guide complet

Cet article aborde le problème courant de la capture des exceptions générées dans des threads distincts de l'appelant méthode. Le problème survient lorsqu'une méthode (Méthode1) génère un nouveau thread et que lors de l'exécution dans ce thread (Méthode2), une exception se produit. Le défi réside dans la transmission de ces informations d'exception à la méthode 1.

Solution

Dans .NET 4 et versions ultérieures, la tâche la classe offre une solution élégante. En utilisant cette classe, vous pouvez :

1. Gestion séparée des exceptions dans les threads des tâches

Dans cette approche, vous pouvez traiter l'exception dans le thread de la tâche, comme le montre l'extrait de code suivant :

class Program
{
    static void Main(string[] args)
    {
        Task<int> task = new Task<int>(Test);
        task.ContinueWith(ExceptionHandler, TaskContinuationOptions.OnlyOnFaulted);
        task.Start();
        Console.ReadLine();
    }

    static int Test()
    {
        throw new Exception();
    }

    static void ExceptionHandler(Task<int> task)
    {
        var exception = task.Exception;
        Console.WriteLine(exception);
    }
}

2. Gérer les exceptions dans le fil de l'appelant

Alternativement, vous pouvez traiter l'exception dans le fil de l'appelant en utilisant ce code :

class Program
{
    static void Main(string[] args)
    {
        Task<int> task = new Task<int>(Test);
        task.Start();

        try
        {
            task.Wait();
        }
        catch (AggregateException ex)
        {
            Console.WriteLine(ex);    
        }

        Console.ReadLine();
    }

    static int Test()
    {
        throw new Exception();
    }
}

Notez que les exceptions obtenues sont de type AggregateException, avec les exceptions réelles stockées dans la propriété ex.InnerExceptions.

.NET 3.5 Solution

Dans .NET 3.5, il existe deux approches :

1. Gestion des exceptions dans Child's Thread

class Program
{
    static void Main(string[] args)
    {
        Exception exception = null;
        Thread thread = new Thread(() => SafeExecute(() => Test(0, 0), Handler));
        thread.Start();            

        Console.ReadLine();
    }

    private static void Handler(Exception exception)
    {        
        Console.WriteLine(exception);
    }

    private static void SafeExecute(Action test, Action<Exception> handler)
    {
        try
        {
            test.Invoke();
        }
        catch (Exception ex)
        {
            Handler(ex);
        }
    }

    static void Test(int a, int b)
    {
        throw new Exception();
    }
}

2. Gestion des exceptions dans le fil de discussion de l'appelant

class Program
{
    static void Main(string[] args)
    {
        Exception exception = null;
        Thread thread = new Thread(() => SafeExecute(() => Test(0, 0), out exception));

        thread.Start();            

        thread.Join();

        Console.WriteLine(exception);    

        Console.ReadLine();
    }

    private static void SafeExecute(Action test, out Exception exception)
    {
        exception = null;

        try
        {
            test.Invoke();
        }
        catch (Exception ex)
        {
            exception = ex;
        }
    }

    static void Test(int a, int b)
    {
        throw new Exception();
    }
}

Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!

Déclaration:
Le contenu de cet article est volontairement contribué par les internautes et les droits d'auteur appartiennent à l'auteur original. Ce site n'assume aucune responsabilité légale correspondante. Si vous trouvez un contenu suspecté de plagiat ou de contrefaçon, veuillez contacter admin@php.cn