Qualcuno può inviare un semplice codice che converte,
System::String^
Per,
C ++ std::string
Cioè, voglio solo assegnare il valore di,
String^ originalString;
Per,
std::string newString;
Risposte:
Non lanciarne uno tuo, usa questi pratici (ed estensibili) wrapper forniti da Microsoft.
Per esempio:
#include <msclr\marshal_cppstd.h>
System::String^ managed = "test";
std::string unmanaged = msclr::interop::marshal_as<std::string>(managed);
Puoi farlo facilmente come segue
#include <msclr/marshal_cppstd.h>
System::String^ xyz="Hi boys";
std::string converted_xyz=msclr::interop::marshal_as< std::string >( xyz);
Questo ha funzionato per me:
#include <stdlib.h>
#include <string.h>
#include <msclr\marshal_cppstd.h>
//..
using namespace msclr::interop;
//..
System::String^ clrString = (TextoDeBoton);
std::string stdString = marshal_as<std::string>(clrString); //String^ to std
//System::String^ myString = marshal_as<System::String^>(MyBasicStirng); //std to String^
prueba.CopyInfo(stdString); //MyMethod
//..
//Where: String^ = TextoDeBoton;
//and stdString is a "normal" string;
Ecco alcune routine di conversione che ho scritto molti anni fa per un progetto c ++ / cli, dovrebbero comunque funzionare.
void StringToStlWString ( System::String const^ s, std::wstring& os)
{
String^ string = const_cast<String^>(s);
const wchar_t* chars = reinterpret_cast<const wchar_t*>((Marshal::StringToHGlobalUni(string)).ToPointer());
os = chars;
Marshal::FreeHGlobal(IntPtr((void*)chars));
}
System::String^ StlWStringToString (std::wstring const& os) {
String^ str = gcnew String(os.c_str());
//String^ str = gcnew String("");
return str;
}
System::String^ WPtrToString(wchar_t const* pData, int length) {
if (length == 0) {
//use null termination
length = wcslen(pData);
if (length == 0) {
System::String^ ret = "";
return ret;
}
}
System::IntPtr bfr = System::IntPtr(const_cast<wchar_t*>(pData));
System::String^ ret = System::Runtime::InteropServices::Marshal::PtrToStringUni(bfr, length);
return ret;
}
void Utf8ToStlWString(char const* pUtfString, std::wstring& stlString) {
//wchar_t* pString;
MAKE_WIDEPTR_FROMUTF8(pString, pUtfString);
stlString = pString;
}
void Utf8ToStlWStringN(char const* pUtfString, std::wstring& stlString, ULONG length) {
//wchar_t* pString;
MAKE_WIDEPTR_FROMUTF8N(pString, pUtfString, length);
stlString = pString;
}
Ho passato ore a cercare di convertire un valore ToString della casella di riepilogo di Windows in una stringa standard in modo da poterlo utilizzare con fstream per l'output in un file txt. Il mio Visual Studio non veniva fornito con i file di intestazione di marshalling che diverse risposte che ho trovato dicevano di usare. Dopo tanti tentativi ed errori ho finalmente trovato una soluzione al problema che utilizza semplicemente System :: Runtime :: InteropServices:
void MarshalString ( String ^ s, string& os ) {
using namespace Runtime::InteropServices;
const char* chars =
(const char*)(Marshal::StringToHGlobalAnsi(s)).ToPointer();
os = chars;
Marshal::FreeHGlobal(IntPtr((void*)chars));
}
//this is the code to use the function:
scheduleBox->SetSelected(0,true);
string a = "test";
String ^ c = gcnew String(scheduleBox->SelectedItem->ToString());
MarshalString(c, a);
filestream << a;
Ed ecco la pagina MSDN con l'esempio: http://msdn.microsoft.com/en-us/library/1b4az623(v=vs.80).aspx
So che è una soluzione piuttosto semplice, ma mi ci sono volute ORE di risoluzione dei problemi e ho visitato diversi forum per trovare finalmente qualcosa che funzionasse.
Ho trovato un modo semplice per ottenere uno std :: string da una String ^ è usare sprintf ().
char cStr[50] = { 0 };
String^ clrString = "Hello";
if (clrString->Length < sizeof(cStr))
sprintf(cStr, "%s", clrString);
std::string stlString(cStr);
Non c'è bisogno di chiamare le funzioni Marshal!
AGGIORNAMENTO Grazie a Eric, ho modificato il codice di esempio per verificare la dimensione della stringa di input per evitare l'overflow del buffer.
C # usa il formato UTF16 per le sue stringhe.
Quindi, oltre a convertire solo i tipi, dovresti anche essere consapevole del formato effettivo della stringa.
Quando si compila per il set di caratteri multibyte, Visual Studio e l'API Win presuppongono UTF8 (in realtà la codifica di Windows che è Windows-28591 ).
Durante la compilazione per il set di caratteri Unicode Visual Studio e l'API Win presuppongono UTF16.
Quindi, è necessario convertire anche la stringa dal formato UTF16 al formato UTF8 e non solo convertirla in std :: string.
Ciò diventerà necessario quando si lavora con formati multi-carattere come alcune lingue non latine.
L'idea è di decidere che rappresenta std::wstring
sempre UTF16 .
E rappresenta std::string
sempre UTF8 .
Questo non viene applicato dal compilatore, è più una buona politica da avere.
#include "stdafx.h"
#include <string>
#include <codecvt>
#include <msclr\marshal_cppstd.h>
using namespace System;
int main(array<System::String ^> ^args)
{
System::String^ managedString = "test";
msclr::interop::marshal_context context;
//Actual format is UTF16, so represent as wstring
std::wstring utf16NativeString = context.marshal_as<std::wstring>(managedString);
//C++11 format converter
std::wstring_convert<std::codecvt_utf8_utf16<wchar_t>> convert;
//convert to UTF8 and std::string
std::string utf8NativeString = convert.to_bytes(utf16NativeString);
return 0;
}
O averlo in una sintassi più compatta:
int main(array<System::String ^> ^args)
{
System::String^ managedString = "test";
msclr::interop::marshal_context context;
std::wstring_convert<std::codecvt_utf8_utf16<wchar_t>> convert;
std::string utf8NativeString = convert.to_bytes(context.marshal_as<std::wstring>(managedString));
return 0;
}
// Ho usato VS2012 per scrivere sotto il codice: convert_system_string in Standard_Sting
#include "stdafx.h"
#include <iostream>
#include <string>
using namespace System;
using namespace Runtime::InteropServices;
void MarshalString ( String^ s, std::string& outputstring )
{
const char* kPtoC = (const char*) (Marshal::StringToHGlobalAnsi(s)).ToPointer();
outputstring = kPtoC;
Marshal::FreeHGlobal(IntPtr((void*)kPtoC));
}
int _tmain(int argc, _TCHAR* argv[])
{
std::string strNativeString;
String ^ strManagedString = "Temp";
MarshalString(strManagedString, strNativeString);
std::cout << strNativeString << std::endl;
return 0;
}