2012-09-28 36 views
7
CString output ; 
const WCHAR* wc = L"Hellow World" ; 
if(wc != NULL) 
{ 
    output.Append(wc); 
} 
printf("output: %s\n",output.GetBuffer(0)); 
+0

Agregue una explicación, como código puro, no dice mucho. – Kao

+0

No necesita GetBuffer. CString tiene un operador LPCTSTR que accede al búfer interno. – MikMik

+1

¿cuál debería ser la salida si 'wc' es' привет мир'? ¿te importan las páginas de códigos o esta es solo una conversión amplia -> estrecha con todos los caracteres anchos siendo caracteres ANSI? –

Respuesta

12

también puede probar esto:

#include <comdef.h> // you will need this 
const WCHAR* wc = L"Hello World" ; 
_bstr_t b(wc); 
const char* c = b; 
printf("Output: %s\n", c); 

_bstr_t implementos siguientes operadores de conversión, que me parece muy útil:

operator const wchar_t*() const throw(); 
operator wchar_t*() const throw(); 
operator const char*() const; 
operator char*() const; 

EDIT: aclaración con respecto a los comentarios de respuesta: la línea const char* c = b; da como resultado una copia de carácter estrecha de la cadena creada y administrada por la instancia _bstr_t que la liberará una vez cuando se destruya. El operador simplemente devuelve un puntero a esta copia. Por lo tanto, no hay necesidad de copiar esta cadena. Además, en la pregunta, CString::GetBuffer devuelve LPTSTR (es decir, TCHAR*) y noLPCTSTR (es decir, const TCHAR*).

Otra opción es el uso de macros de conversión:

USES_CONVERSION; 
const WCHAR* wc = L"Hello World" ; 
const char* c = W2A(wc); 

El problema con este enfoque es que la memoria de cadena convertida se asigna en la pila, por lo que la longitud de la cadena es limitado. Sin embargo, esta familia de macros de conversión le permite seleccionar la página de códigos que se utilizará para la conversión, que a menudo se necesita si la cadena ancha contiene caracteres que no son ANSI.

+0

Estoy tan tentado de hacer +1 de esto. '_bstr_t' y' _variant_t' solían ser mis mejores amigos en los días en que realmente necesitabas que ATL hiciera un componente COM decente en C++ – sehe

+0

pero no copió wc en c – jack

+0

¿por qué iba a copiarlo? su código muestra que necesita usarlo en 'printf'. '_bstr_t' se ocupará de liberar la memoria.Si necesita conservar una copia y enviar la cadena, use la instancia '_bstr_t', no' const char * '- en este sentido,' _bstr_t' es similar a 'CString'. Se encarga de copiar los datos de cadena correctamente cuando se utilizan varias copias del objeto (aunque no utiliza * copy-on-write *). –

1

Se podría hacer esto, o se podría hacer algo más limpio:

std::wcout << L"output: " << output.GetString() << std::endl; 
+1

¿Por qué usar 'GetBuffer()'? ¡Aquí está el getter oficial Get-String() 'C-string! – Rost

+0

@Rost copiar y pegar: D No hay necesidad de gritar: D –

+2

Copiar y pegar es malo !!! ¡Los desarrolladores reales siempre vuelven a escribir char por char! ¿No lo sabes?!? :-D – Rost

1

Es bastante fácil, porque CString es sólo un typedef para CStringT, y también tiene acceso a CStringA y CStringW (usted debe leer la documentación acerca de las diferencias).

CStringW myString = L"Hello World"; 
CString myConvertedString = myString; 
+0

'CStringA myConvertedString (L "Hello World");' también funciona – Rost

+0

Sí, me doy cuenta de eso, pero estaba escrito que manera de estar más cerca de su código de ejemplo. –

+0

¿Qué hace esta conversión con caracteres anchos que no tienen un carácter angosto coincidente? –

5

Se puede utilizar para este propósito sprintf:

const char output[256]; 
const WCHAR* wc = L"Hellow World" ; 
sprintf(output, "%ws", wc); 
+0

No creo que puedas declarar 'output' como' const' – CinCout

2

Mi código para Linux

// Debian GNU/Linux 8 "Jessie" (amd64) 

#include <locale.h> 
#include <stdlib.h> 
#include <stdio.h> 

// Use wcstombs(3) to convert Unicode-string (wchar_t *) to UTF-8 (char *) 
// http://man7.org/linux/man-pages/man3/wcstombs.3.html 

int f(const wchar_t *wcs) { 
     setlocale(LC_ALL,"ru_RU.UTF-8"); 
     printf("Sizeof wchar_t: %d\n", sizeof(wchar_t)); 
     // on Windows, UTF-16 is internal Unicode encoding (UCS2 before WinXP) 
     // on Linux, UCS4 is internal Unicode encoding 
     for (int i = 0; wcs[i] > 0; i++) printf("%2d %08X\n",i,wcs[i]); 
     char s[256]; 
     size_t len = wcstombs(s,wcs,sizeof(s)); 
     if (len > 0) { 
       s[len] = '\0'; 
       printf("mbs: %s\n",s); 
       for (int i = 0; i < len; i++) 
         printf("%2d %02X\n",i,(unsigned char)s[i]); 
       printf("Size of mbs, in bytes: %d\n",len); 
       return 0; 
     } 
     else return -1; 
} 

int main() { 
     f(L"Привет"); // 6 symbols 
     return 0; 
} 

¿Cómo construir

#!/bin/sh 
NAME=`basename $0 .sh` 
CC=/usr/bin/g++-4.9 
INCS="-I." 
LIBS="-L." 
$CC ${NAME}.c -o _${NAME} $INCS $LIBS 

salida

$ ./_test 
Sizeof wchar_t: 4 
0 0000041F 
1 00000440 
2 00000438 
3 00000432 
4 00000435 
5 00000442 
mbs: Привет 
0 D0 
1 9F 
2 D1 
3 80 
4 D0 
5 B8 
6 D0 
7 B2 
8 D0 
9 B5 
10 D1 
11 82 
Size of mbs, in bytes: 12 
Cuestiones relacionadas