105 votes

Qu'est-ce qu'un handle en C++ ?

On m'a dit qu'un handle est en quelque sorte un pointeur, mais non, et qu'il permet de conserver une référence à un objet, plutôt que l'objet lui-même. Quelle est l'explication la plus élaborée ?

7 votes

2 votes

Si vous examinez le modèle de la chaîne de responsabilité, vous apprendrez qu'un "Handle" est essentiellement un nœud, et qu'un "Handler" est un petit ensemble de nœuds. La "magie" vient de la récursion

104voto

Matthew Iselin Points 5843

Un handle peut être n'importe quoi, d'un indice entier à un pointeur vers une ressource dans l'espace du noyau. L'idée est qu'ils fournissent une abstraction d'une ressource, de sorte que vous n'avez pas besoin d'en savoir beaucoup sur la ressource elle-même pour l'utiliser.

Par exemple, le HWND dans l'API Win32 est un handle pour une fenêtre. En soi, il est inutile : vous ne pouvez pas en tirer d'informations. Mais si vous le passez aux bonnes fonctions de l'API, vous pouvez l'utiliser pour une multitude d'astuces différentes. En interne, vous pouvez considérer le HWND comme un simple index dans la table des fenêtres de l'interface graphique (ce n'est pas nécessairement la façon dont il est implémenté, mais cela donne un sens à la magie).

EDIT : Je ne suis pas sûr à 100% de ce que vous demandiez spécifiquement dans votre question. Il s'agit principalement de C/C++ pur.

14 votes

Un Handle peut être utile pour sauvegarder des états (entre autres). Si vous avez des données dans une structure comme un std::vector. Votre objet peut se trouver à différents emplacements mémoire à différents moments de l'exécution d'un programme, ce qui signifie que votre pointeur vers cette mémoire changera de valeur. Avec un handle, il ne change jamais, il référence toujours votre objet. Imaginez que vous sauvegardiez l'état d'un programme (comme dans un jeu) - vous ne sauvegarderiez pas un emplacement de pointeur vers des données pour ensuite importer à nouveau les données et essayer d'obtenir cette adresse en mémoire. Vous pouvez cependant sauvegarder un Handle avec vos données, et importer les données et le Handle.

0 votes

Est-il possible de convertir un HANDLE en un équivalent sous Linux ? Je dois faire migrer un programme qui utilise HANDLE de Windows à Linux.

1 votes

C'est la bonne réponse, ils peuvent être n'importe quoi, et le code qui les utilise définit le type de poignée. J'ai essayé de faire une version plus concise de ma propre réponse similaire, je n'ai pas pu m'en empêcher, pour la postérité. @CornelVerster - Ils sont les mêmes sous linux. Je veux dire, pas les handles de l'OS, mais le concept. Donc, cela dépend du handle quant à sa migration, ou même la nécessité de migrer.

57voto

jmucchiello Points 10521

Un handle est un pointeur ou un index auquel aucun type visible n'est attaché. Habituellement, vous voyez quelque chose comme :

 typedef void* HANDLE;
 HANDLE myHandleToSomething = CreateSomething();

Ainsi, dans votre code, vous passez simplement HANDLE comme une valeur opaque.

Dans le code qui utilise l'objet, il convertit le pointeur en un type de structure réel et l'utilise :

 int doSomething(HANDLE s, int a, int b) {
     Something* something = reinterpret_cast<Something*>(s);
     return something->doit(a, b);
 }

Ou il l'utilise comme un index dans un tableau/vecteur :

 int doSomething(HANDLE s, int a, int b) {
     int index = (int)s;
     try {
         Something& something = vecSomething[index];
         return something.doit(a, b);
     } catch (boundscheck& e) {
         throw SomethingException(INVALID_HANDLE);
     }
 }

31voto

Deltics Points 9213

Une poignée est une sorte de pointeur dans la mesure où il s'agit typiquement d'un moyen de référencer une entité.

Il serait plus exact de dire qu'un pointeur est un type de poignée, mais que toutes les poignées ne sont pas des pointeurs.

Par exemple, un handle peut aussi être un index dans une table en mémoire, qui correspond à une entrée qui contient elle-même un pointeur vers un objet.

Ce qui est important, c'est que lorsque vous avez une "poignée", vous ne savez pas et ne vous souciez pas de savoir comment cette poignée finit par identifier la chose qu'elle identifie, tout ce que vous devez savoir, c'est qu'elle le fait.

Il devrait également être évident qu'il n'y a pas de réponse unique à la question "qu'est-ce qu'un handle", car les handles de différentes choses, même dans le même système, peuvent être implémentés de différentes manières "sous le capot". Mais vous ne devriez pas avoir à vous préoccuper de ces différences.

6voto

Mehrdad Afshari Points 204872

En C++/CLI, un handle est un pointeur vers un objet situé sur le tas GC. La création d'un objet sur le tas C++ (non géré) est réalisée à l'aide de la commande new et le résultat d'un new est un pointeur "normal". Un objet géré est alloué sur le tas GC (géré) avec une valeur gcnew expression. Le résultat sera un handle. Vous ne pouvez pas faire d'arithmétique de pointeur sur les handles. On ne libère pas les handles. Le GC s'en occupe. De plus, le GC est libre de relocaliser des objets sur le tas géré et de mettre à jour les handles pour qu'ils pointent vers les nouveaux emplacements pendant l'exécution du programme.

5voto

Cela apparaît dans le contexte de la Poignée-Corps-Idiome également appelé idiome Pimpl. Il permet de conserver l'ABI (interface binaire) d'une bibliothèque en conservant les données réelles dans un objet d'une autre classe, qui est simplement référencé par un pointeur contenu dans un objet "handle", composé de fonctions déléguées à cette classe "Body".

Il est également utile de permettre l'échange de deux objets en temps constant et sans risque d'exception. Pour cela, il suffit de permuter le pointeur pointant vers l'objet corps.

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X