Tests et branchements

Sur cette page

Les instructions de test

Comment présenter les instructions de test

L'instruction de branchement

La foncion IIF()

Fonctions de validation

Validation de paramètres

Exemple 1: Tester si une cellule Excel nommée "Nombre" contient un nombre.

Exemple 2: Programmer une fonction qui retourne le nom d'une province, à partir d'un sigle.

Sommaire

Fichier exemples

 

Boucles

Gestion d'erreur

Collections et tableaux

Dialogues et formulaires

Objets et événements Excel

Conseils de programmation

Liste d'instructions

Les instructions de test

Les instructions d'un programme sont normalement exécutées les unes à la suite des autres, séquentiellement.
Les instructions de test, de boucle et de branchement permettent de modifier cet ordre naturel.

If expression Then
   
[instructions]
[Else
    [instructions]]
End If

  • expression Une expression VBA qui est évaluée à Vrai ou Faux. Si expression vaut Null, elle est considéré comme Faux.

  • instructions Une ou plusieurs instructions VBA, sur autant de lignes que nécessaire.

La première série d'instructions est exécutée si expression vaut Vrai, et la seconde si expression vaut Faux

À la version de base ci-dessus qui ne permet que 2 alternatives, s'ajoutent les variations suivantes:

If expression Then instructions

  • expression Une expression VBA qui est évaluée à Vrai, Faux ou Null.

  • instructions Une ou plusieurs instructions VBA séparées par des : qui seront exécutées si expression vaut Vrai

Il est fortement recommandé de ne JAMAIS utiliser cette forme de IF qui n'ajoute rien et rend le programme plus difficile à comprendre et plus difficile à modifier. Utilisez plutôt:

If expression Then
   
[instructions]
End If

 

If expression Then
   
[instructions]
[ElseIF
    [instructions]]
[ElseIF
    [instructions]]
    ...
[Else
   
[instructions]]
End If

  • expression Une expression VBA qui est évaluée à Vrai ou Faux. Si expression vaut Null, elle est considéré comme Faux.

  • instructions Une ou plusieurs instructions VBA

Chaque série d'instructions est exécutée si l'expression précédente vaut Vrai, sauf celle qui suit le Else, qui est exécutée quand aucune des précédentes n'est Vraie.

Cette variante du If est recommandée si votre programme doit tester plus d'une valeur d'une expression.

 

Select Case expression
    [Case liste/expression
        [instructions]] ...
    [Case Else
        [instructions]]
End Select

  • expression expression VBA
  • liste/expression Liste de valeur(s) possibles(s) pour expression ou expresseion VBA.
  • instructions  Une ou plusieurs instructions VBA

Cette instruction VBA joue le même rôle que le IF... ELSEIF ... ENDIF précédent, mais est plus difficile à coder et à comprendre.
À éviter.

Autres fonctions de test à ne jamais utiliser:

Dim rRéponse
rRéponse = Switch(expression1,valeur1[, expression2, valeur2, expression3, valeur3, expression4, valeur4… [, expressionN, valeurN]])

 

Qui correspond à:

 

Dim rRéponse
If expression1 THEN
   
rRéponse = valeur1
ELSEIF expression3
THEN
   
rRéponse = valeur2

ELSE
    rRéponse = Null
ENDIF

 

Dim rRéponse
rRéponse = Choose(expression, valeur1[, valeur2, ... [, valeurN]])

Qui correspond à:

Dim rRéponse
If expression=1 THEN
   
rRéponse = valeur1
ELSEIF expression=2
THEN
   
rRéponse = valeur2

...
ELSE
    rRéponse = Null
ENDIF

Présentation des instructions de test

En VBA, il est convenu de présenter en retrait les instructions à l'intérieur d'un bloc de test.

Exemples à éviter:

If B > A Then A = B 'Ne pas faire de If sans Endif

If B > A Then
A = B 'Mettre les instructions d'un If en retrait
End If

Présentez ce test ainsi:

If B > A Then
    A = B 'Le retrait permet d'identifier les instructions
             'Dont l'exécution est conditionnelle au If
End If     'Le Endif permet d'identifier la fin du If

L'instruction de branchement

VBA hérite des anciennes versions de Basic une instruction de branchement, qui modifie la séquence d'exécution
en effectuant un branchement vers une ligne identifiée par une étiquette.

La syntaxe de l'étiquette est:

nom:

nom respecte la syntaxe d'une variable VBA, et doit être suivi d'un deux points (:)

L'instruction
GoTo
étiquette
peut être utilisée n'importe où à l'intérieur de la procédure (pas du module!) pour indiquer que la suite
du traitement se trouve aux lignes suivant l'étiquette.

L'utilisation de GoTo n'est vraiment acceptable qu'à l'intérieur d'une instruction On Error.
Dans d'autres circonstances, elle rend la logique du programme difficile à comprendre, donc à modifier.

La fonction IIf()

VBA inclut la fonction IIf() qui fonctionne exactement comme la fonction Si() de Excel (français) ou If() (Excel anglais):

IIf(expression, ValeurVrai, ValeurFaux)

Où:

  • expression Expression à évaluer.
  • ValeurVrai Valeur renvoyée si la valeur de expression est True.
  • ValeurFaux Valeur renvoyée si la valeur de expression est False.

Fonctions de validation

VBA offre plusieurs séries de fonctions utiles pour valider la nature des données et des variables.

IsNumeric(expression) Vrai si expression peut être évaluée comme une valeur numérique 
IsDate(expression) Vrai si expression peut être évaluée comme une date ou une heure 

 

IsNull(expression) Vrai si expression ne contient aucune variable de valeur Null.
Attention:
expression = Null
expression <> Null
sont TOUJOURS faux. Utilisez IsNull(Variable).
(variableobjet) Is Nothing Vrai si variableobjet est un objet non initialisé (voir SET).
IsEmpty(expression) Vrai si expression est de type Variant et n'est pas initialisée.
IsMissing(paramètre) paramètre  doit être le nom d'un paramètre facultatif de la procédure en cours.
Faux si une valeur a été passée dans paramètre.

 

IsObject(variable) Vrai si variable est de type Object.
Utilisez plutôt la fonction TypeName()
IsArray(variable) Vrai si variable est une variable contenant un tableau VBA.

 

TypeName(variable) Retourne le nom du type de variable, exemples:
  • Currency
  • Currency() - tableau de type currency
  • Date
  • Null
  • Object
  • Empty
    mais aussi:
  • Range
  • WorkSheet
  • ...
VarType(variable) Retourne une entier indiquant le type de variable.
Beaucoup moins intéressant que TypeName().

Validation de paramètres

On a vu dans la section Déclarations qu'il est préférable de déclarer Variant les paramètres d'une Function ou d'un Sub paramétré.

En effet, il est impossible de prédire au moment de la programmation quel type de paramètre sera transmis à la Function ou au Sub.

Développons à une fonction fnNomMois qui retourne le nom du mois d'une date fournie en paramètre: Function fnNomMois(dDate As Date)
'Auteur: Michel Berthiaume
'Retourne le nom du mois de la date
'fournie en paramètre

    fnNomMois = Format(dDate, "mmmm")

End Function
Notez qu'on pourrait utiliser l'instruction IF et la fonction VBA Month() pour arriver au même résultat. Mais le code serait plus long et retournerait le nom de mois dans une seule langue.
Le code à gauche utilise la fonction VBA Format pour obtenir le nom du mois de l'environnement Windows (donc dans la langue de l'utilisateur)
fnNomMois(#2012-1-2#) retourne janvier  
fnNomMois(2012-1-2) retourne juillet Parce que 2012 moins 1 moins 2 vaut 2009 et que le numéro de jour 2009 correspond au 1er juillet 1905. VBA fait une conversion automatique non souhaitée.
Il est donc préférable de ne pas déclarer le type du paramètre et de plutôt en tester le type: Function fnNomMois(dDate)
'Auteur: Michel Berthiaume
'Retourne le nom du mois de la date
'fournie en paramètre

If IsDate(dDate) Then
    fnNomMois = Format(dDate, "mmmm")
Else
    fnNomMois = "Date invalide"
End If

End Function
L'utilisateur sera alors informé qu'il a mal formulé le paramètre
Maintenant
fnNomMois(2012-1-2)

retourne Date invalide
 
Si la cellule Excel

A1 contient 2012-01-02
A1 ne contient rien

A1 contient 2012-02-31

A1 contient janvier

et B1 contient =fnNomMois(A1)

B1 affiche janvier
B1 affiche Date invalide

B1 affiche Date invalide

B1 affiche Date invalide

 

 

Exemples

Exemple 1: Tester si une cellule Excel nommée "Nombre" contient un nombre.

Sub sExempleTest1()
'Auteur: Michel Berthiaume
'Vérifier si la cellule "Nombre" contient un nombre
    If IsNumeric(Range("Nombre").Value) Then
        MsgBox"La valeur est numérique"
    End If

    'Suite de la procédure
    '...

End Sub

Bien qu'intéressant, ce code n'est pas très fonctionnel.
Il affiche un message lorsque la cellule contient une valeur numérique (ou nulle),
mais ce qu'on veut probablement, c'est interrompre la suite de la procédure lorsque la valeur n'est pas numérique.

Sub sExempleTest2()
'Auteur: Michel Berthiaume
'Vérifier si la cellule "Nombre" contient un nombre
    If Not IsNumeric(Range("Nombre").Value) Then
        MsgBox"La valeur n'est pas numérique"
        Exit Sub
    End If
    'Suite de la procédure
    '...

End Sub


Exemple 2: Programmer une fonction qui retourne le nom d'une province, à partir d'un sigle.

Function fnNomProvince1(SigleProvince)
'Auteur: Michel Berthiaume
'Retourner le nom d'une province
Dim sSigleProvince As String

On Error GoTo Erreur:

    'D'abord tester la validité du paramètre
    If TypeName(SigleProvince) = "Range" Then
        sSigleProvince = UCase(SigleProvince.Value)
    Else
        If TypeName(SigleProvince) = "String" Then
            sSigleProvince = UCase(SigleProvince)
        Else
            fnNomProvince1 = "sigle inconnu"
            Exit Function
        End If
    End If

    'Rendu ici, sSigleProvince contient une version en majuscules du sigle
    If sSigleProvince = "AB" Then
        fnNomProvince1 = "Alberta"
    Else
        If sSigleProvince = "BC" Then
            fnNomProvince1 = "Colombie Britannique"
        Else
            If sSigleProvince = "PE" Then
                fnNomProvince1 = "Île-du-Prince-Édouard"
            Else
                If sSigleProvince = "NS" Then
                    fnNomProvince1 = "Nouvelle-Écosse"
                Else
                    If sSigleProvince = "NU" Then
                        fnNomProvince1 = "Nunavut"
                    Else
                        If sSigleProvince = "ON" Then
                            fnNomProvince1 = "Ontario"
                        Else
                            If sSigleProvince = "QC" Then
                                fnNomProvince1 = "Québec"
                            Else
                                If sSigleProvince = "SK" Then
                                    fnNomProvince1 = "Saskatchewan"
                                Else
                                    If sSigleProvince = "NF" Then
                                        fnNomProvince1 = "Terre Neuve"
                                    Else
                                        If sSigleProvince = "NT" Then
                                            fnNomProvince1 = "Territoires du Nord-Ouest"
                                        Else
                                            If sSigleProvince = "YK" Then
                                                fnNomProvince1 = "Yukon"
                                            Else
                                                fnNomProvince1 = "Sigle inconnu"
                                            End If
                                        End If
                                    End If
                                End If
                            End If
                        End If
                    End If
                End If
            End If
        End If
    End If

    Exit Function
Erreur:
    fnNomProvince1 = "Erreur: " & Err.Description
End Function

 

Bien que fonctionnel, le code ci-dessus est lourd et répétitif.
Voici une version allégée:

Function fnNomProvince2(SigleProvince)
'Auteur: Michel Berthiaume
'Retourner le nom d'une province
Dim sSigleProvince As String

On Error GoTo Erreur:

    'D'abord tester la validité du paramètre
    If TypeName(SigleProvince) = "Range" Then
        sSigleProvince = UCase(SigleProvince.Value)
    Else
        If TypeName(SigleProvince) = "String" Then
            sSigleProvince = UCase(SigleProvince)
        Else
            fnNomProvince2 = "sigle inconnu"
            Exit Function
        End If
    End If

    'Rendu ici, sSigleProvince contient une version en majuscules du sigle
    If sSigleProvince = "AB" Then
        fnNomProvince2 = "Alberta"
    ElseIf sSigleProvince = "BC" Then
        fnNomProvince2 = "Colombie Britannique"
    ElseIf sSigleProvince = "PE" Then
        fnNomProvince2 = "Île-du-Prince-Édouard"
    ElseIf sSigleProvince = "NS" Then
        fnNomProvince2 = "Nouvelle-Écosse"
    ElseIf sSigleProvince = "NU" Then
        fnNomProvince2 = "Nunavut"
    ElseIf sSigleProvince = "ON" Then
        fnNomProvince2 = "Ontario"
    ElseIf sSigleProvince = "QC" Then
        fnNomProvince2 = "Québec"
    ElseIf sSigleProvince = "SK" Then
        fnNomProvince2 = "Saskatchewan"
    ElseIf sSigleProvince = "NF" Then
        fnNomProvince2 = "Terre Neuve"
    ElseIf sSigleProvince = "NT" Then
        fnNomProvince2 = "Territoires du Nord-Ouest"
    ElseIf sSigleProvince = "YK" Then
        fnNomProvince2 = "Yukon"
    Else
        fnNomProvince2 = "Sigle inconnu"
    End If

    Exit Function
Erreur:
    fnNomProvince2 = "Erreur: " & Err.Description
End Function

 

Il est aussi possible d'utiliser l'Instruction SELECT, mais elle n'offre pas d'avantage important sur la version précédente:

 

Function fnNomProvince3(SigleProvince)
'Auteur: Michel Berthiaume
'Retourner le nom d'une province
Dim sSigleProvince As String

On Error GoTo Erreur:

    'D'abord tester la validité du paramètre
    If TypeName(SigleProvince) = "Range" Then
        sSigleProvince = UCase(SigleProvince.Value)
    Else
        If TypeName(SigleProvince) = "String" Then
            sSigleProvince = UCase(SigleProvince)
        Else
            fnNomProvince3 = "sigle inconnu"
            Exit Function
        End If
    End If

 'Rendu ici, sSigleProvince contient une version en majuscules du sigle
    Select Case sSigleProvince
        Case "AB"
            fnNomProvince3 = "Alberta"
        Case "BC"
            fnNomProvince3 = "Colombie Britannique"
        Case "PE"
            fnNomProvince3 = "Île-du-Prince-Édouard"
        Case "NS"
            fnNomProvince3 = "Nouvelle-Écosse"
        Case "NU"
            fnNomProvince3 = "Nunavut"
        Case "ON"
            fnNomProvince3 = "Ontario"
        Case "QC"
            fnNomProvince3 = "Québec"
        Case "SK"
            fnNomProvince3 = "Saskatchewan"
        Case "NF"
            fnNomProvince3 = "Terre Neuve"
        Case "NT"
            fnNomProvince3 = "Territoires du Nord-Ouest"
        Case "YK"
            fnNomProvince3 = "Yukon"
        Case Else
            fnNomProvince3 = "Sigle inconnu"
    End Select

    Exit Function
Erreur:
    fnNomProvince3 = "Erreur: " & Err.Description
End Function

Sommaire

VBA offre plusieurs structures contrôlant l'ordre d'exécution des instructions.

Fichier exemples

Le fichier Excel Exemples Tests.xlsm contient les exemples présentés dans la présente section.

Suite: Boucles