Passage d'un argument par valeur et par référence (Visual Basic)

En Visual Basic, vous pouvez passer un argument à une procédure par valeur ou par référence. Cette opération est appelée mécanisme de passage et détermine si la procédure peut modifier l'élément de programmation sous-jacent à l'argument dans le code appelant. La déclaration de procédure détermine le mécanisme de passage pour chaque paramètre en spécifiant le mot clé Byval (Visual Basic) ou ByRef (Visual Basic).

Distinctions

Lorsque vous passez un argument à une procédure, informez-vous des diverses distinctions qui ont une interaction entre elles :

  • L'élément de programmation sous-jacent est-il modifiable ou non modifiable ?

  • L'argument lui-même est-il modifiable ou non modifiable ?

  • L'argument est-il passé par valeur ou par référence ?

  • Le type de données d'argument est-il un type valeur ou un type référence ?

Pour plus d'informations, consultez Différences entre les arguments modifiables et non modifiables (Visual Basic) et Différences entre le passage d'un argument par valeur et par référence (Visual Basic).

Choix du mécanisme de passage

Vous devez choisir avec soin le mécanisme de passage pour chaque argument.

  • Protection. Lors du choix d'un mécanisme de passage, le critère le plus important est la fréquence à laquelle les variables d'appel doivent changer. Le passage d'un argument par ByRef permet à la procédure de retourner une valeur au code appelant via cet argument. Le passage d'un argument par ByVal permet d'empêcher une variable d'être modifiée par la procédure.

  • Performances. Bien que le mécanisme de passage puisse affecter les performances de votre code, la différence est généralement insignifiante. La seule exception à cette règle est le passage d'un type valeur par ByVal. Dans ce cas, Visual Basic copie tout le contenu des données de l'argument. Par conséquent, dans le cas d'un type valeur de grande taille tel qu'une structure, il peut être préférable d'effectuer un passage ByRef.

    Pour les types référence, seul le pointeur vers les données est copié (quatre octets sur les plateformes 32 bits, huit octets sur les plateformes 64 bits). Par conséquent, vous pouvez passer des arguments de type String ou Object par valeur sans nuire aux performances.

Détermination du mécanisme de passage

La déclaration de procédure spécifie le mécanisme de passage pour chaque paramètre. Le code appelant ne peut pas substituer un mécanisme d' ByVal .

Si un paramètre est déclaré avec ByRef, le code appelant peut forcer le mécanisme à ByVal en plaçant le nom de l'argument entre parenthèses dans l'appel. Pour plus d’informations, consultez Comment : forcer le passage d'un argument par valeur (Visual Basic).

Le comportement par défaut en Visual Basic consiste à passer les arguments par valeur.

Quand passer un argument par valeur

  • Si l'élément de code appelant sous-jacent à l'argument est un élément non modifiable, déclarez le paramètre Byval (Visual Basic) correspondant. Aucun code ne peut modifier la valeur d'un élément non modifiable.

  • Si l'élément sous-jacent est modifiable, et si vous ne souhaitez pas que la procédure puisse modifier sa valeur, déclarez le paramètre ByVal. Seul le code appelant peut modifier la valeur d'un élément modifiable passée par valeur.

Quand passer un argument par référence

  • Si la procédure nécessite véritablement que l'élément sous-jacent dans le code appelant soit modifié, déclarez le paramètre ByRef (Visual Basic) correspondant.

  • Si l'exécution correcte du code dépend de la procédure modifiant l'élément sous-jacent dans le code appelant, déclarez le paramètre ByRef. Si vous le passez par valeur ou si le code appelant substitue le mécanisme de passage ByRef en mettant l'argument entre parenthèses, l'appel de procédure peut produire des résultats inattendus.

Exemple

Description

L'exemple suivant indique quand les arguments doivent être passés par valeur ou par référence. La procédure Calculate contient à la fois les paramètres ByVal et ByRef. À partir d'un taux d'intérêt, rate, et d'une somme d'argent, debt, la tâche de la procédure consiste à calculer une nouvelle valeur pour debt qui est le résultat de l'application du taux d'intérêt à la valeur d'origine de debt. Étant donné que debt est un paramètre ByRef, le nouveau total est représenté dans la valeur de l'argument du code appelant qui correspond à debt. rate est un paramètre ByVal car Calculate ne doit pas modifier sa valeur.

Code

Module Module1

    Sub Main()
        ' Two interest rates are declared, one a constant and one a  
        ' variable. 
        Const highRate As Double = 12.5
        Dim lowRate = highRate * 0.6

        Dim initialDebt = 4999.99
        ' Make a copy of the original value of the debt. 
        Dim debtWithInterest = initialDebt

        ' Calculate the total debt with the high interest rate applied. 
        ' Argument highRate is a constant, which is appropriate for a  
        ' ByVal parameter. Argument debtWithInterest must be a variable 
        ' because the procedure will change its value to the calculated 
        ' total with interest applied.
        Calculate(highRate, debtWithInterest)
        ' Format the result to represent currency, and display it. 
        Dim debtString = Format(debtWithInterest, "C")
        Console.WriteLine("What I owe with high interest: " & debtString)

        ' Repeat the process with lowRate. Argument lowRate is not a  
        ' constant, but the ByVal parameter protects it from accidental 
        ' or intentional change by the procedure.  

        ' Set debtWithInterest back to the original value.
        debtWithInterest = initialDebt
        Calculate(lowRate, debtWithInterest)
        debtString = Format(debtWithInterest, "C")
        Console.WriteLine("What I owe with low interest:  " & debtString)
    End Sub 

    ' Parameter rate is a ByVal parameter because the procedure should 
    ' not change the value of the corresponding argument in the  
    ' calling code.  

    ' The calculated value of the debt parameter, however, should be 
    ' reflected in the value of the corresponding argument in the  
    ' calling code. Therefore, it must be declared ByRef.  
    Sub Calculate(ByVal rate As Double, ByRef debt As Double)
        debt = debt + (debt * rate / 100)
    End Sub 

End Module

Voir aussi

Tâches

Comment : passer des arguments à une procédure (Visual Basic)

Comment : modifier la valeur d'un argument de la procédure (Visual Basic)

Comment : protéger un argument de procédure contre les modifications de valeur (Visual Basic)

Comment : forcer le passage d'un argument par valeur (Visual Basic)

Concepts

Procédures dans Visual Basic

Paramètres et arguments d'une procédure (Visual Basic)

Passage des arguments par position et par nom (Visual Basic)

Types valeur et types référence