Vue d'ensemble de la gestion structurée des exceptions pour Visual Basic

Mise à jour : Juillet 2008

Visual Basic prend en charge la gestion structurée des exceptions, qui vous permet de créer et de gérer des programmes à l'aide de gestionnaires d'erreurs robustes et complets. La gestion structurée des exceptions est conçue sous forme de code pour détecter et répondre aux erreurs d'exécution en associant une structure de contrôle (semblable à Select Case ou While) à des exceptions, des blocs de code protégés et des filtres.

L'instruction Try...Catch...Finally vous permet de protéger des blocs de code qui présentent le risque de générer des erreurs. Vous pouvez imbriquer les gestionnaires d'exceptions ; en outre, les variables déclarées dans chaque bloc auront une portée locale.

Try...Catch...Finally, instruction

Le code suivant illustre la structure d'une instruction Try...Catch...Finally.

Try
    ' Starts a structured exception handler.
    ' Place executable statements that may generate 
    ' an exception in this block.
Catch '[optional filters]
    ' This code runs if the statements listed in 
    ' the Try block fail and the filter on the Catch statement is true.
'[Additional Catch blocks]
Finally
    ' This code always runs immediately before
    ' the Try statement exits.
End Try
' Ends a structured exception handler.

Le bloc Try d'un gestionnaire d'exceptions Try...Catch...Finally contient la section de code dans laquelle il faut contrôler les exceptions. Si une erreur se produit durant l'exécution de cette section, Visual Basicexamine chaque instruction Catch du bloc Try...Catch...Finally jusqu'à ce qu'il en trouve une correspondant à l'erreur. Si une instruction est trouvée, le contrôle est transféré vers la première ligne de code du bloc Catch. Si aucune instruction Catch correspondante n'est trouvée, la recherche se poursuit sur les instructions Catch du bloc Try...Catch...Finally extérieur qui contient le bloc dans lequel l'exception s'est produite. Ce processus se poursuit dans la pile entière jusqu'à ce qu'un bloc Catch correspondant soit trouvé dans la procédure en cours. Si la recherche est infructueuse, une erreur se produit.

Le code de la section Finally s'exécute toujours en dernier, juste avant la fin de la portée du bloc de gestion d'erreur, indépendamment du fait que le code des blocs Catch se soit exécuté ou non. Placez le code de nettoyage, par exemple pour fermer des fichiers et libérer des objets, dans la section Finally. Si vous n'êtes pas obligé d'intercepter les exceptions, mais que vous devez nettoyer les ressources, envisagez l'utilisation de l'instruction Using plutôt que d'une section Finally. Pour plus d'informations, consultez Using, instruction (Visual Basic).

Filtrage des erreurs dans le bloc Catch

Les blocs Catch permettent l'utilisation de trois options pour filtrer les erreurs spécifiques. Dans un cas, les erreurs sont filtrées selon la classe de l'exception (ici ClassLoadException), comme indiqué dans le code suivant.

Try
    ' "Try" block.
Catch e as ClassLoadException
    ' "Catch" block.
Finally
    ' "Finally" block.
End Try

Si une erreur ClassLoadException se produit, le code contenu dans le bloc Catch spécifié s'exécute.

Dans le deuxième cas de filtrage des erreurs, la section Catch peut filtrer toutes les expressions conditionnelles. L'utilisation la plus courante de ce type de filtre Catch permet de tester des numéros d'erreur spécifiques, comme indiqué dans le code suivant.

Try
   ' "Try" block.
Catch When ErrNum = 5 'Type mismatch.
   ' "Catch" block.
Finally
   ' "Finally" block.
End Try

Lorsque Visual Basic trouve le gestionnaire d'erreur correspondant, il exécute le code contenu dans ce gestionnaire, puis passe le contrôle au bloc Finally.

Remarque :

Lors d'une tentative de recherche d'un bloc Catch pour gérer une exception, chaque gestionnaire de bloc est évalué jusqu'à la découverte d'une correspondance. Puisque ces gestionnaires peuvent être des appels à des fonctions, des effets secondaires inattendus peuvent se produire ; par exemple, un appel de ce type pourrait modifier une variable publique qui est ensuite utilisée dans le code d'un bloc Catch différent qui finit par gérer l'exception.

Une troisième alternative consiste à associer la première et la deuxième option et à utiliser ces deux options pour la gestion des exceptions. Vos instructions Catch doivent aller de la plus spécifique à la moins spécifique. Un bloc Catch par lui-même interceptera toutes les exceptions dérivées de Exception et par conséquent doit toujours être le dernier bloc avant Finally.

Branchement en dehors de blocs Try...Catch

Il est possible de créer une branche à partir d'un bloc Catch vers l'instruction Try initiale ou l'instruction End Try, mais il n'est pas possible de créer une branche vers un bloc Try…Catch englobant. En voici une illustration :

Branchement Try Catch

Exemple de gestionnaire d'exceptions structuré

L'exemple suivant illustre un autre gestionnaire d'erreur de base utilisant l'instruction Try...Catch...Finally.

Option Strict On
Imports System.IO

Module Module1
    Private Const FileName As String = "TestFile.data"

    Public Sub Main()

        ' First, create a new data file and write some data to the file.
        ' 1. Create the new, empty data file.
        If File.Exists(FileName) Then
            File.Delete(FileName)
        End If
        Dim fs As New FileStream(FileName, FileMode.CreateNew)

        ' 2. Create a BinaryWriter object for the data.
        Dim writer As New BinaryWriter(fs)

        ' 3. Write some sample data to the file.
        For i = 0 To 10
            writer.Write(i)
        Next i
        writer.Close()
        fs.Close()

        ' Now read from the file you just made.
        ' 1. Create a BinaryReader object for the data stream.
        fs = New FileStream(FileName, FileMode.Open, FileAccess.Read)
        Dim reader As New BinaryReader(fs)

        ' 2. Read data from TestFile.data. The loop terminates with an
        ' EndOfStreamException when an attempt is made to read past
        ' the end of the stream.
        Try
            ' This loop terminates with an EndOfStreamException when it 
            ' reaches the end of the stream.
            While True
                Console.WriteLine(reader.ReadInt32())
            End While
            Console.WriteLine("The data was read with no error.")
        ' 3. Report the first error that is caught, if there is one.
        Catch eosExcep As EndOfStreamException
            ' This Catch block is executed when the reader attempts
            ' to read past the end of the stream.
            Console.WriteLine("End-of-stream exception occurred.")
        Catch IOExcep As System.IO.IOException
            ' For this Catch block, some other error occurred before
            ' the end of stream was reached. Print the standard
            ' exception message.
            Console.WriteLine(IOExcep.Message)
        Finally
            ' The Finally block is always executed.
            Console.WriteLine("Executing the Finally block.")
            reader.Close()
            fs.Close()
        End Try
    End Sub

End Module

Le bloc Finally est toujours exécuté, quelle que soit l'action qui se produit dans les blocs Catch précédents. Vous ne pouvez pas utiliser Resume ni Resume Next dans la gestion structurée des exceptions.

Remarque :

Dans l'exemple précédent, toute exception autre que la classe IOException ou la classe EndOfStreamException est retournée non gérée à l'appelant.

Voir aussi

Tâches

Résolution des problèmes liés à la gestion des exceptions

Concepts

Introduction à la gestion des exceptions

Types d'erreurs

Vue d'ensemble de la gestion non structurée des exceptions

Référence

Try...Catch...Finally, instruction (Visual Basic)

BinaryReader

BinaryWriter

FileStream

Autres ressources

Tâches de gestion des exceptions

Historique des modifications

Date

Historique

Raison

Juillet 2008

Exemple remplacé dans la section « Exemple de gestionnaire d'exceptions structuré  ».

Commentaires client.