Article de reference

Type de valeur et type de référence

Dans certains langages de programmation informatique , les types de données sont classés en types de valeur ou types de référence , où les types de référence sont toujours acces...

Dans certains langages de programmation informatique , les types de données sont classés en types de valeur ou types de référence , où les types de référence sont toujours accessibles implicitement via des références , tandis que les variables de type de valeur contiennent directement les valeurs elles-mêmes.

Propriétés des types de valeur et des types de référence

Même parmi les langages qui ont cette distinction, les propriétés exactes des types de valeur et de référence varient d'un langage à l'autre, mais les propriétés typiques incluent :

  • Les types de données primitifs , tels que les booléens, les entiers de taille fixe, les valeurs à virgule flottante et les caractères, sont des types de valeur.
  • Les objets, au sens de la programmation orientée objet , appartiennent à des types de référence.
  • L'affectation à une variable de type référence copie simplement la référence, tandis que l'affectation à une variable de type valeur copie la valeur. Cela s'applique à tous les types de variables, y compris les variables locales, les champs d'objets et les éléments de tableau. De même, lors de l'appel d'une fonction : les paramètres de type référence sont des copies de la référence, tandis que les paramètres de type valeur sont des copies de la valeur.
  • Si un type de référence est mutable , les mutations effectuées via une référence sont visibles via n'importe quelle autre, alors que si un type de valeur est mutable, les mutations effectuées sur une valeur ne sont pas visibles dans une autre.
  • Les types de référence prennent en charge la notion d' identité : il est logique de discuter si deux valeurs de type de référence font référence au même objet, et le langage fournit des fonctionnalités pour déterminer si elles le font, alors que les types de valeur ne le font pas.
  • Les valeurs de type référence font référence aux objets alloués dans le tas, tandis que les valeurs de type valeur sont contenues soit dans la pile d'appels (dans le cas de variables locales et de paramètres de fonction), soit à l'intérieur de leurs entités contenantes (dans le cas de champs d'objets et d'éléments de tableau). (Avec les types référence, seule la référence elle-même est contenue soit dans la pile d'appels, soit à l'intérieur d'une entité contenante.)
  • Les types de référence prennent en charge la notion de sous-typage , selon laquelle toutes les valeurs d'un type de référence donné sont automatiquement des valeurs d'un type de référence différent. Les types de valeur ne prennent pas en charge le sous-typage, mais peuvent prendre en charge d'autres formes de conversion de type implicite , par exemple la conversion automatique d'un entier en nombre à virgule flottante si nécessaire. De plus, il peut y avoir des conversions implicites entre certains types de valeur et de référence, par exemple la « mise en boîte » d'une primitive int(un type de valeur) en un Integerobjet (un type d'objet), ou l'inversion via le « déballage ».

Types de référence et « appel par partage »

Même lorsque les arguments de fonction sont transmis à l'aide de la sémantique « appel par valeur » (ce qui est toujours le cas en Java et par défaut en C#), une valeur d'un type de référence est intrinsèquement une référence ; donc si un paramètre appartient à un type de référence, le comportement qui en résulte ressemble quelque peu à la sémantique « appel par référence ». Ce comportement est parfois appelé appel par partage .

L'appel par partage ressemble à l'appel par référence dans le cas où une fonction mute un objet qu'elle a reçu en argument : lorsque cela se produit, la mutation sera également visible pour l'appelant, car l'appelant et la fonction ont des références au même objet. Il diffère de l'appel par référence dans le cas où une fonction affecte son paramètre à une référence différente ; lorsque cela se produit, cette affectation ne sera pas visible pour l'appelant, car l'appelant et la fonction ont des références distinctes , même si les deux références pointent initialement vers le même objet.

Types de référence et pointeurs explicites

De nombreux langages ont des pointeurs ou des références explicites . Les types de référence diffèrent de ceux-ci dans la mesure où les entités auxquelles ils font référence sont toujours accessibles via des références ; par exemple, alors qu'en C++, il est possible d'avoir soit a soit a , où le premier est une chaîne mutable et le second est un pointeur explicite vers une chaîne mutable (à moins qu'il ne s'agisse d'un pointeur nul), en Java, il est uniquement possible d'avoir a , qui est implicitement une référence vers une chaîne mutable (à moins qu'il ne s'agisse d'une référence nulle). std::stringstd::string*StringBuilder

Bien que l'approche de C++ soit plus flexible, l'utilisation de non-références peut entraîner des problèmes tels que le découpage d'objets , au moins lorsque l'héritage est utilisé ; dans les langages où les objets appartiennent à des types de référence, ces problèmes sont automatiquement évités, au prix de la suppression de certaines options du programmeur.

Reliure et alias de référence

Dans la plupart des langages de programmation, il est possible de modifier la variable d'un type de référence pour faire référence à un autre objet, c'est-à-dire de relier la variable à un autre objet.

Par exemple, dans le code Java suivant :

classe 
Foo { public int a ; }
Foo a = nouveau Foo (); Foo b = a ; a . prop = 3 ; a = nouveau Foo (); a . prop = 1 ;

Fooest un type de référence, où aest initialement assignée une référence d'un nouvel objet, et best assignée à la même référence d'objet, c'est-à-dire liée au même objet que a, par conséquent, les changements via asont également visibles pour baussi bien. Ensuite, aest assignée une référence (rebond) à un autre nouvel objet, et maintenant aet bfait référence à des objets différents. À la fin, afait référence au deuxième objet avec son propchamp ayant la valeur 1, tandis que bfait référence au premier objet avec son propchamp ayant la valeur 3.

Cependant, comme en C++, le terme « type de référence » est utilisé pour désigner un alias, et il n'est pas possible de relier une variable d'un type de référence une fois qu'elle est créée, car il s'agit d'un alias de l'objet d'origine.

struct Foo { int a ; };
Foo a ; a . prop = 1 ; Foo & b = a ; Foo c = a ; a . prop = 3 ;

En C++, tous les types de classes non référencées ont une sémantique de valeur. Dans l'exemple ci-dessus, best déclaré comme étant une référence (alias) de a, et à toutes fins utiles, aet bsont la même chose. Il est impossible de le relier bpour devenir quelque chose d'autre. Une fois l'exemple ci-dessus exécuté, aet bsont le même Fooobjet avec propétant 3, tandis que cest une copie de l'original aavec propétant 1.

En C#, outre la distinction entre les types de valeur et les types de référence, il existe également un concept distinct appelé variables de référence. Une variable de référence, une fois déclarée et liée, se comporte comme un alias de la variable d'origine, mais elle peut également être liée à une autre variable en utilisant l'opérateur d'affectation de référence = ref. La variable elle-même peut être de n'importe quel type, y compris les types de valeur et les types de référence, c'est-à-dire qu'en passant une variable d'un type de référence par référence (alias) à une fonction, l'objet vers lequel pointe la variable de type de référence peut également être modifié, en plus de l'objet lui-même (s'il est mutable).

Types de données immuables

Si un objet est immuable et que l'égalité des objets est testée sur le contenu plutôt que sur l'identité, la distinction entre le type de valeur et les types de référence n'est plus claire, car l'objet lui-même ne peut pas être modifié, mais seulement remplacé dans son intégralité (pour le type de valeur) / avec la référence pointée vers un autre objet (pour le type de référence). Le passage de tels objets immuables entre variables n'entraîne aucune différence observable si l'objet est copié ou passé par référence, à moins que l'identité de l'objet ne soit prise. Dans un langage de programmation fonctionnel où rien n'est mutable (comme Haskell), une telle distinction n'existe pas du tout et devient un détail d'implémentation.

Classification par langue

Plus d articles de Worldlex Wiki

Revenez a l index pour explorer davantage de pages sur l histoire, la science, la culture, la geographie et la societe en francais.

Explorer l index