천객만래 [千客萬來] (It has an interminable succession of visitors)

[개발/VC++] 유니코드 버전으로 된 프로젝트에서 CString 를 char* 로 바꾸는 방법





MFC에서 유니코드 버전으로 된 프로젝트에서 CString 를 char* 로 바꾸는 방법은
유니코드 상태에서 CString 을 바로 CHAR* 로 바꾸는 것이 안됩니다.

W2A 나 A2W 로 코드 변환을 하거나 wsprintf(); 함수를 이용 하면 됩니다.

유니코드는 사용 되는 바이트 수가 2바이트이고 1바이트 문자열로 변환하면 깨져 버리는 문자열 들이 있는데  처리를 해야 합니다. 

유니코드를 멀티바이트 코드로 변환 하려면 

char Text[80];
wsprintfA(Text, "%S", L"문자열" );

멀티바이트 코드를 유니코드로 변환 하려면 

WCHAR Text[80];
wsprintfW(Text, L"%S", "문자열" );


변환될 문자열을 %S(대문자)로 wsprintf()함수를 사용합니다.

※ 현재로써는 바로 CString 에서 char*(LPSTR , LPCSTR) 로 변환 할수 없습니다. 

참고로 더 설명을 하면 CString 기본 요소는 CStringBase<WCHAR>  , CStringBase<CHAR> 둘로 나누어집니다.
이 두 클래스 사이에서 바로 입력 변환이 불가능 합니다. 

변환시에는 API 함수로 코드 변환 후에 사용 해야 하며 
CStringBase<CHAR> 로 사용 한다면 유니코드 내에서 ANSI 코드를 사용 할 수 있습니다. 

또 다른 방법의 함수
-----------------------------
CString을 유니코드로

CString tmp("test");
WCHAR m_wPath[MAX_PATH];

wcscpy(wPath,tmp.GetBuffer(0));



Posted by SB패밀리


문자관련 함수

MBCS(multi-byte character set) : ASCII 코드 문자열을 쓰는 함수
WCS(wide character string) : 유니코드 문자열을 쓰는 함수

함수 제일 뒤에 ASCII를 나타내는 A와 Wide Character를 나타내는 W를 붙여서 구분함.
예)  GetCurrentDirectoryA ...
예외) cout, wcout

LPCTSTR(Long Pointer Constant TCHAR String)
여기서 TCHAR 라는 것은 typedef  유니코드가 설정되어 있으면 2바이트로(wchar_t) 아니면 기존 char 방식인 1바이트로(char) 한다는 것을 의미.

LPSTR : 8비트 윈도우 캐릭터 스트링(string) 포인터 문자.
LPCSTR : LPSTR 와 같고 단지 상수형(Constant )이라는 포인터문자.

참조:
http://cafe.naver.com/whatvoip.cafe?iframe_url=/ArticleRead.nhn%3Farticleid=225


--> MFC의 CString 은 TCHAR 형이다.

ATL 형변환 메크로

종류는 [소스 타입]2[새로운 타입][소스 타입]2C[새로운 타입] 이 있다.
여기서 2C의 C는 const형(읽기전용)이라는 뜻이다.

ATL 3.0 String Conversion Macros

A2BSTR OLE2A T2A W2A
A2COLE OLE2BSTR T2BSTR W2BSTR
A2CT OLE2CA T2CA W2CA
A2CW OLE2CT T2COLE W2COLE
A2OLE OLE2CW T2CW W2CT
A2T OLE2T T2OLE W2OLE
A2W OLE2W T2W W2T



여기서 A, W, T, OLE, BSTR이 있는데 그 의미는 다음과 같다.

A : MBCS 스트링, char* (A 는 ANSI를 의미) -> LPSTR
W : Unicode 스트링, wchar_t* (W는 wide를 의미) -> LPWSTR
T : TCHAR 스트링, TCHAR* -> LPTSTR
OLE : OLECHAR 스트링, OLECHAR* (사실, W와 같은 의미) -> LPOLESTR
BSTR : BSTR

이를 통해 몇가지 메크로를 분석해 보면

매크로 인자 결과
A2CW (LPCSTR) (LPCWSTR)
A2W (LPCSTR) (LPWSTR)
W2CA (LPCWSTR) (LPCSTR)
W2A (LPCWSTR) (LPSTR)
T2COLE (LPCTSTR) (LPCOLESTR)
T2OLE (LPCTSTR) (LPOLESTR)
OLE2CT (LPCOLESTR) (LPCTSTR)
OLE2T (LPCOLESTR) (LPCSTR)



*사용법:
#include <atlconv.h>
void func( LPSTR lpsz )
{
   USES_CONVERSION; //형변환 메크로를 사용하기 위해서.
   ...
   LPWSTR x = A2W(lpsz)
   // Do something with x
   ...
}

*사용시 주의점:
이 매크로는 메모리를 스택에 잡음:
1) 과도한 순환문 속에서는 사용하면 안됨.
   - 매크로가 불릴 때마다 스택의 메모리를 잡아먹습니다.
   - 그 메모리는 함수가 끝날 때까지 해제되지 않습니다.
2) 매크로의 결과를 리턴하면 안됨.
   - 결과로 나오는 포인터는 함수가 끝날 때까지만 유효합니다.

참조 :
http://msdn.microsoft.com/en-us/library/87zae4a3(VS.80).aspx
http://jof4002.net/?Unicode
http://eroom.korea.com/post/board.aspx?bid=kmh_19505&mode=read&view=board&pid=189103&page=1


LPWSTR to CString

(CString) 으로 캐스팅하면 끝


CString to LPWSTR

CString strString = "abcd";
BSTR bstrString = strString.AllocSysString();
LPWSTR pwstr = (LPWSTR)bstrString;
SysFreeString(bstrString);

CString to LPTSTR

CString str = _T("new text");

  LVITEM item = {0};
 
  item.mask = LVIF_TEXT;
  item.iItem = 1;
  item.pszText = (LPTSTR)(LPCTSTR) str; // 잘못된 사용!
  // 올바른 사용.
  /*1)*/ item.pszText = str.GetBuffer();
  // 또는
  /*2)*/ _tcscpy_s(item.pszText, MAX_PATH, str.GetBuffer(str.GetLength()));
  ListView_SetItem ( &item );
  str.ReleaseBuffer();

참조 :
http://eroom.korea.com/post/board.aspx?bid=kmh_19505&mode=read&view=board&pid=189103&page=1

CString to DWORD

CString str=_T("abcd");
DWORD dw = (DWORD)_ttoi((LPCTSTR)str);


출처 : http://hogwarts.tistory.com/172
Posted by SB패밀리

MFC에서 유니코드 버전으로 된 프로젝트에서 CString 를 char* 로 바꾸는 방법은
유니코드 상태에서 CString 을 바로 CHAR* 로 바꾸는 것이 안됩니다.

W2A 나 A2W 로 코드 변환을 하거나 wsprintf(); 함수를 이용 하면 됩니다.

유니코드는 사용 되는 바이트 수가 2바이트이고 1바이트 문자열로 변환하면 깨져 버리는 문자열 들이 있는데  처리를 해야 합니다.

유니코드를 멀티바이트 코드로 변환 하려면

char Text[80];
wsprintfA(Text, "%s", L"문자열" );

멀티바이트 코드를 유니코드로 변환 하려면

WCHAR Text[80];
wsprintfW(Text, L"%s", "문자열" );


변환될 문자열을 %s(대문자)로 wsprintf()함수를 사용합니다.

※ 현재로써는 바로 CString 에서 char*(LPSTR , LPCSTR) 로 변환 할수 없습니다.

참고로 더 설명을 하면 CString 기본 요소는 CStringBase<WCHAR>  , CStringBase<CHAR> 둘로 나누어집니다.
이 두 클래스 사이에서 바로 입력 변환이 불가능 합니다.

변환시에는 API 함수로 코드 변환 후에 사용 해야 하며 
CStringBase<CHAR> 로 사용 한다면 유니코드 내에서 ANSI 코드를 사용 할 수 있습니다.

또 다른 방법의 함수
-----------------------------
CString을 유니코드로

CString tmp("test");
WCHAR m_wPath[MAX_PATH];

wcscpy(wPath,tmp.GetBuffer(0));

Posted by SB패밀리


CString -> char *

CString str;
str = "Hello";
char* ss = LPSTR(LPCTSTR(str));

 

char * --> CString

char ss[] = "Hello";
CString str;
str.Format("%s", ss);

(Format대신에 GetBuffer()를 써도 됩니다.)
 
지식인!
 
Environment: Compiled using VC6.0 Sp3 and tested using Win95/98 WinNT4.0 and Win 2000
Here are a few data Conversions with small examples :-

PART ONE :- DECIMAL CONVERSIONS
Decimal To Hexa :-
Use _itoa( ) function and set radix to 16.

 

char hexstring[10];
int number = 30;
itoa( number, hexstring, 16);

In hexstring is 1e.

Hexa To Decimal :-
a)You can use strtol function and you can specify base.

char * hexstring= "ABCDEF";
char * p;
int number = strtol(hexstring, &p,16);

b) Or you can use this too

bool HexToDecimal (char* HexNumber, int& Number)
{
char* pStopString;
Number = strtol (HexNumber, &pStopString, 16);
return (bool)(Number != LONG_MAX);
}


Decimal to Time :-

char *DecToTime(float fTime, char *szTime)
{
int nHrs, nMin, nSec;
fTime *= 3600;
nHrs = (int)fTime / 3600;
nMin = (int)(fTime - nHrs * 3600) / 60;
nSec = (int)(fTime - nHrs * 3600 - nMin * 60);
wsprintf(szTime, "%02d.%02d.%02d Hrs.Min.Sec.", nHrs, nMin, nSec);
return szTime;
}

PART TWO :- STRING CONVERSIONS
String to Hexa :-

sscanf(string, %04X, &your_word16);
// where string = your string and 04 = length of your string and X = hex


Hex to CString :-
CString Str;
unsigned char Write_Buff[1];
Write_Buff[0] = 0x01;
Str.Format("0x0%x",Write_Buff[0]);


COleVariant to CString :-
CString strTemp;
COleVariant Var;
Var = "FirstName";
strTemp = Var.bstrVal;
AfxMessageBox(strTemp);


CString to Char Pointer :-
a) CString MyString = "ABCDEF";
char * szMyString = (char *) (LPCTSTR) MyString;

b) char *pBuffer = new char[1024];
CString strBuf = "Test";
pBuffer = strBuf.GetBuffer(sizeof(pBuffer));

 

Char Pointer to CString :-
char * mystring = "12345";
CString string = mystring;


Double to CString including the fractional part :-
CString strValue,strInt, strDecimal;
int decimal,sign;
double dValue = 4.125;
strValue = _fcvt(dValue,6,&decimal,&sign);

// Now decimal contains 1 because there is only one digit before the .

strInt = strValue.Left(decimal); // strInt contains 4
strDecimal = strValue.Mid(decimal); // strDecimal contains 125

CString strFinalVal;
strFinalVal.Format("%s.%s",strInt,strDecimal); // strFinalVal contains 4.125

 

Double To CString :-
CString strValue;
int decimal,sign;

double dValue = 123456789101112;
strValue = _ecvt(dValue,15,&decimal,&sign);


CString To Double :-
strValue = "121110987654321";
dValue = atof(strValue);


CString to LPCSTR :-
CString str1 = _T("My String");
int nLen = str1.GetLength();
LPCSTR lpszBuf = str1.GetBuffer(nLen);
// here do something with lpszBuf...........
str1.ReleaseBuffer();


CString to LPSTR :-
CString str = _T("My String");
int nLen = str.GetLength();
LPTSTR lpszBuf = str.GetBuffer(nLen);
// here do something with lpszBuf...........
str.ReleaseBuffer();

CString to WCHAR* :-
CString str = "A string here" ;
LPWSTR lpszW = new WCHAR[255];

LPTSTR lpStr = str.GetBuffer( str.GetLength() );
int nLen = MultiByteToWideChar(CP_ACP, 0,lpStr, -1, NULL, NULL);
MultiByteToWideChar(CP_ACP, 0, lpStr, -1, lpszW, nLen);
AFunctionUsesWCHAR( lpszW );
delete[] lpszW;

 

LPTSTR to LPWSTR :-
int nLen = MultiByteToWideChar(CP_ACP, 0, lptStr, -1, NULL, NULL);
MultiByteToWideChar(CP_ACP, 0, lptStr, -1, lpwStr, nLen);


string to BSTR
string ss = "Girish";
BSTR _bstr_home = A2BSTR(ss.c_str());


CString to BSTR :-
CString str = "whatever" ;
BSTR resultsString = str.AllocSysString();


_bstr_t to CString :-

#include
#include
_bstr_t bsText("Hai Bayram");
CString strName;
W2A(bsText, strName.GetBuffer(256), 256);
strName.ReleaseBuffer();
AfxMessageBox(strName);

char szFileName[256];
GetModuleFileName(NULL,szFileName,256);
AfxMessageBox(szFileName);


PART THREE :- CHARACTER ARRAYS

Char array to integer
char MyArray[20];
int nValue;

nValue = atoi(MyArray);

 

Char array to float
char MyArray[20];
float fValue;

fValue = atof(MyArray);


Char Pointer to double :-
char *str = " -343.23 ";
double dVal;
dVal = atof( str );


Char Pointer to integer :-
char *str = " -343.23 ";
int iVal;
iVal = atoi( str );

 

Char Pointer to long :-
char *str = "99999";
long lVal;
lVal = atol( str );


Char* to BSTR :-
char * p = "whatever";
_bstr_t bstr = p;

Float to WORD and Vice Versa :-
float fVar;
WORD wVar;
fVar = 247.346;
wVar = (WORD)fVar; //Converting from float to WORD. The value in wVar would be 247
wVar = 247;
fVar = (float)fVar; //Converting from WORD to float. The value in fVar would be 247.00

# cstring to int

int 형 = _ttoi(cstring 형)


# int to cstring

cstring 형.Format( _T("%d"), int 형); 
 
* CString -> std::string

 

CString cs ("Hello");

  // Convert a TCHAR string to a LPCSTR
  CT2CA pszConvertedAnsiString (cs);

  // construct a std::string using the LPCSTR input
  std::string strStd (pszConvertedAnsiString);

 

 

* std::string -> CString

 

CString tmp;

string foo;

tmp = foo.c_str();

Posted by SB패밀리