Condividi tramite


Procedura: accedere ai caratteri in System::String

È possibile accedere ai caratteri di un String oggetto per chiamate ad alte prestazioni a funzioni non gestite che accettano wchar_t* stringhe. Il metodo restituisce un puntatore interno al primo carattere dell'oggetto String . Questo puntatore può essere modificato direttamente o aggiunto e passato a una funzione che prevede una stringa normale wchar_t .

Esempi

PtrToStringCharsrestituisce un Charoggetto , che è un puntatore interno (noto anche come ).byref Di conseguenza, è soggetto a Garbage Collection. Non è necessario aggiungere questo puntatore a meno che non venga passato a una funzione nativa.

Si consideri il codice seguente. L'aggiunta non è necessaria perché ppchar è un puntatore interno e se il Garbage Collector sposta la stringa a cui punta, aggiornerà ppcharanche . Senza un pin_ptr (C++/CLI), il codice funzionerà e non avrà il potenziale impatto sulle prestazioni causato dall'aggiunta.

Se si passa ppchar a una funzione nativa, deve essere un puntatore di blocco. Il Garbage Collector non sarà in grado di aggiornare i puntatori nello stack frame non gestito.

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

int main() {
   String ^ mystring = "abcdefg";

   interior_ptr<const Char> ppchar = PtrToStringChars( mystring );

   for ( ; *ppchar != L'\0'; ++ppchar )
      Console::Write(*ppchar);
}
abcdefg

Questo esempio mostra dove è necessaria l'aggiunta.

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

size_t getlen(System::String ^ s) {
   // Since this is an outside string, we want to be secure.
   // To be secure, we need a maximum size.
   size_t maxsize = 256;
   // make sure it doesn't move during the unmanaged call
   pin_ptr<const wchar_t> pinchars = PtrToStringChars(s);
   return wcsnlen(pinchars, maxsize);
};

int main() {
   System::Console::WriteLine(getlen("testing"));
}
7

Un puntatore interno ha tutte le proprietà di un puntatore C++ nativo. Ad esempio, è possibile usarlo per esaminare una struttura di dati collegata ed eseguire inserimenti ed eliminazioni usando un solo puntatore:

// PtrToStringChars_3.cpp
// compile with: /clr /LD
using namespace System;
ref struct ListNode {
   Int32 elem;
   ListNode ^ Next;
};

void deleteNode( ListNode ^ list, Int32 e ) {
   interior_ptr<ListNode ^> ptrToNext = &list;
   while (*ptrToNext != nullptr) {
      if ( (*ptrToNext) -> elem == e )
         *ptrToNext = (*ptrToNext) -> Next;   // delete node
      else
         ptrToNext = &(*ptrToNext) -> Next;   // move to next node
   }
}

Vedi anche

Uso delle funzionalità di interoperabilità C++ (PInvoke implicito)