Partager via


Comment : déclarer des handles dans les types natifs

Vous ne pouvez pas déclarer un type de handle dans un type natif. vcclr.h fournit le modèle gcroot wrapper de type sécurisé pour faire référence à un objet CLR à partir du tas C++. Ce modèle vous permet d’incorporer un handle virtuel dans un type natif et de le traiter comme s’il s’agissait du type sous-jacent. Dans la plupart des cas, vous pouvez utiliser l’objet gcroot comme type incorporé sans cast. Toutefois, avec chacune d’elles, vous devez utiliser static_cast pour récupérer la référence managée sous-jacente.

Le gcroot modèle est implémenté à l’aide des installations de la classe de valeur System ::Runtime ::InteropServices ::GCHandle, qui fournit des « handles » dans le tas collecté par la mémoire. Notez que les handles eux-mêmes ne sont pas collectés par la mémoire et sont libérés lorsqu’ils ne sont plus utilisés par le destructeur dans la gcroot classe (ce destructeur ne peut pas être appelé manuellement). Si vous instanciez un gcroot objet sur le tas natif, vous devez appeler la suppression sur cette ressource.

Le runtime conserve une association entre le handle et l’objet CLR, qu’il référence. Lorsque l’objet CLR se déplace avec le tas collecté par le garbage, le handle retourne la nouvelle adresse de l’objet. Une variable n’a pas besoin d’être épinglée avant d’être affectée à un gcroot modèle.

Exemples

Cet exemple montre comment créer un gcroot objet sur la pile native.

// mcpp_gcroot.cpp
// compile with: /clr
#include <vcclr.h>
using namespace System;

class CppClass {
public:
   gcroot<String^> str;   // can use str as if it were String^
   CppClass() {}
};

int main() {
   CppClass c;
   c.str = gcnew String("hello");
   Console::WriteLine( c.str );   // no cast required
}
hello

Cet exemple montre comment créer un gcroot objet sur le tas natif.

// mcpp_gcroot_2.cpp
// compile with: /clr
// compile with: /clr
#include <vcclr.h>
using namespace System;

struct CppClass {
   gcroot<String ^> * str;
   CppClass() : str(new gcroot<String ^>) {}

   ~CppClass() { delete str; }

};

int main() {
   CppClass c;
   *c.str = gcnew String("hello");
   Console::WriteLine( *c.str );
}
hello

Cet exemple montre comment utiliser gcroot pour contenir des références à des types valeur (et non des types référence) dans un type natif à l’aide gcroot du type boxed.

// mcpp_gcroot_3.cpp
// compile with: /clr
#include < vcclr.h >
using namespace System;

public value struct V {
   String^ str;
};

class Native {
public:
   gcroot< V^ > v_handle;
};

int main() {
   Native native;
   V v;
   native.v_handle = v;
   native.v_handle->str = "Hello";
   Console::WriteLine("String in V: {0}", native.v_handle->str);
}
String in V: Hello

Voir aussi

Utilisation de l’interopérabilité C++ (PInvoke implicite)