Cómo: serializar cadenas Unicode mediante la interoperabilidad de C++How to: Marshal Unicode Strings Using C++ Interop

En este tema se muestra una faceta de la interoperabilidad de Visual C++.This topic demonstrates one facet of Visual C++ interoperability. Para obtener más información, vea usar la interoperabilidad de C++ (implicit PInvoke).For more information, see Using C++ Interop (Implicit PInvoke).

En los siguientes ejemplos de código se usan las directivas de #pragma administradas y no administradas para implementar funciones administradas y no administradas en el mismo archivo, pero estas funciones interoperan de la misma manera si se definen en archivos independientes.The following code examples use the managed, unmanaged #pragma directives to implement managed and unmanaged functions in the same file, but these functions interoperate in the same manner if defined in separate files. No es necesario compilar los archivos que contienen solo funciones no administradas con /CLR (compilación de Common Language Runtime).Files containing only unmanaged functions do not need to be compiled with /clr (Common Language Runtime Compilation).

En este tema se muestra cómo se pueden pasar cadenas Unicode de una función administrada a una función no administrada y viceversa.This topic demonstrates how Unicode strings can be passed from a managed to an unmanaged function, and vice versa. Para interoperar con otros tipos de cadenas, vea los temas siguientes:For interoperating with other strings types, see the following topics:

Ejemplo: pasar una cadena Unicode de una función administrada a una función no administradaExample: Pass Unicode string from managed to unmanaged function

Para pasar una cadena Unicode de una función administrada a una función no administrada, se puede usar la función PtrToStringChars (declarada en vcclr. h) para tener acceso a en la memoria donde se almacena la cadena administrada.To pass a Unicode string from a managed to an unmanaged function, the PtrToStringChars function (declared in Vcclr.h) can be used to access in the memory where the managed string is stored. Dado que esta dirección se pasará a una función nativa, es importante que la memoria se ancle con pin_ptr (C++/CLI) para evitar que los datos de cadena se reubiquen, en caso de que se produzca un ciclo de recolección de elementos no utilizados mientras se ejecuta la función no administrada.Because this address will be passed to a native function, it is important that the memory be pinned with pin_ptr (C++/CLI) to prevent the string data from being relocated, should a garbage collection cycle take place while the unmanaged function executes.

// MarshalUnicode1.cpp
// compile with: /clr
#include <iostream>
#include <stdio.h>
#include <vcclr.h>

using namespace std;

using namespace System;
using namespace System::Runtime::InteropServices;

#pragma unmanaged

void NativeTakesAString(const wchar_t* p) {
   printf_s("(native) received '%S'\n", p);
}

#pragma managed

int main() {
   String^ s = gcnew String("test string");
   pin_ptr<const wchar_t> str = PtrToStringChars(s);

   Console::WriteLine("(managed) passing string to native func...");
   NativeTakesAString( str );
}

Ejemplo: serialización de datos necesaria para obtener acceso a una cadena UnicodeExample: Data marshaling required to access Unicode string

En el ejemplo siguiente se muestra el cálculo de referencias de datos necesario para tener acceso a una cadena Unicode en una función administrada a la que llama una función no administrada.The following example demonstrates the data marshaling required to access a Unicode string in a managed function called by an unmanaged function. La función administrada, al recibir la cadena Unicode nativa, la convierte en una cadena administrada mediante el PtrToStringUni método.The managed function, on receiving the native Unicode string, converts it to a managed string using the PtrToStringUni method.

// MarshalUnicode2.cpp
// compile with: /clr
#include <iostream>

using namespace std;
using namespace System;
using namespace System::Runtime::InteropServices;

#pragma managed

void ManagedStringFunc(wchar_t* s) {
   String^ ms = Marshal::PtrToStringUni((IntPtr)s);
   Console::WriteLine("(managed) received '{0}'", ms);
}

#pragma unmanaged

void NativeProvidesAString() {
   cout << "(unmanaged) calling managed func...\n";
   ManagedStringFunc(L"test string");
}

#pragma managed

int main() {
   NativeProvidesAString();
}

Consulte tambiénSee also

Usar la interoperabilidad de C++ (PInvoke implícito)Using C++ Interop (Implicit PInvoke)