728x90
반응형

음성인식엔진 개발자 출신으로서, 자연어처리/기계번역 분야에서  입력 글자 처리하는 루틴은 상당히 난해한 분야입니다.

 

프로그램을 보면,
MString 과 UString의 클래스가 있으면, 빈번히 변환한다.
 
사유 ::  소켓 통신할 때와,  프로젝트의 기반 세트가 다를 때, 빈번히 변환을 해 주어야 한다.
 
사유 :: 다국어 작업(번역)을 하다보면, 멀티바이트에서 언어가 깨지는 문제가 발생한다. 이 때 유니코드로 변환해서 적용을 해준다면, 깨지는 문제는 해결된다.
 
#문자세트(Character Set)의 종류와 특성
     . SBCS(Single Byte Character Set) :: 문자를 표현하는데 1Byte를 사용-ASCII
     . MBCS(Multi Byte Character Set) ::  한글은 2Byte, 영문은 1Byte -MultiByte(다중바이트), 다중 은 꼴랑 1개이냐? 2개이냐?  
     . WBCS(Wide Byte Character Set) ::  모든 문자를 2Byte 사용 - Unicode  ( 통일코드) ..  통일이 꼴랑 2로 했남?,  Uni가 1개? Wide가 넓게... 이름 참 희안하게 ....  ( 2^16 즉  65,536개....)  Uni는 1개의 뜻이 아니라  Unique의 뜻....(고유의 코드값)
 
 
# 멀티바이트 문자 집합은  특정문자 집합마다의 코드 페이지가 존재한다.
   예를 들어, 같은 코드 번호 일지라도 한글 코드페이지로 해석하면 한글이 나오지만,   일어코드 페이지로 해석하면 일어가 나온다. 
 
 
MULTI-BYTE ( ISO-2200 :: 가변바이트)
(ANSI, UTF-8)
:: UTF-8 ( 1~4바이트) :: 1,112,064자 표현 가능
WIDE-CHAR 자료형...
 유니코드
(Windows, Java에서는 UTF-16,
나머지 시스템에서는 UTF-8)
비고
string wstring CA2W("멀티바이트를 유니코드로 변환")
CW2A("유니코드를 멀티바이트로 변환")
CW2A("유니코드를 UTF8로 변환", CP_UTF8)
char *



strlen()
CString
WCHAR
wchar_t
L"유니코드"
lstrlenW()
TCHAR는 char인지, wchar인지 구별하지 않고 코딩
컴파일러에서 기본을 설절함에 따라, 일괄 변경된다...
LPCSTR LPCWSTR LP :: Long Pointer
C : Const

MultiByteToWideChar()   Windows OS에서만 가능
 
WideCharToMultiByte()
Windows OS에서만 가능
    CP_ACP  ::  시스템에서 사용하는 MBCS(멀티바이트) -> UTF-16(유니코드)
CP_UTF8->UTF-16(유니코드)
     
 
 
MFC에서
 
유니코드->멀티바이트
 
char * ConvertUnicodeToMultiByte( CString strUnicode)
{
         int nLen = WideCharToMultiByte( CP_ACP, 0, strUnicode, -1, NULL, 0, NULL, NULL);   # 변환 대상에 대한 크기, 길이정보를 구한다. 변환 후의 크기....  widechar가 2바이트짜리, 3바이트짜리가 있으니....계산해서.. multibyte의 크기를 출력...
        
        char* pMultiByte = new char(nLen);
        memset( pMultiByte, 0x00, nLen * sizeof(char) );
 
        WideChartoMultiByte( CP_ACP, 0, strUnicode, -1, pMultiByte, nLen, NULL, NULL);            // {유니코드}->{멀티바이트}.[ASCII  또는 UTF-8],     CP_ACP(아스키),  CP_UTF8
 
       retrun pMultiByte;
}
 
wchar_t strUnicode[256]={0,};
char      strMultibyte[256]={0,};
wcscpy(strUnicode, 256, L"유니코드");
int  len = WideCharToMultiByte( CP_ACP, 0, strUnicode, -1, NULL, 0, NULL, NULL);
WideCharToMultiByte(CP_ASCP, 0, strUnicode, -1, strMultibyte, len, NULL, NULL);
 
 
유니코드->UTF-8
wchar_t strUni[256]=L"유니코드";
char      strUtf8[256]={0, };
int nLen = WideCharToMultiByte( CP_UTF8, 0, strUni, lstrlenW(strUni), NULL, 0, NULL, NULL);
WideCharToMultiByte( CP_UTF8, 0, strUni, lstrlenW(strUni), strUtf8, nLen, NULL, NULL);
 
 
 
 
멀티바이트->유니코드
 
CString ConvertMultibyteToUnicode(char *pMultibyte)
{
     int nLen = strlen(pMultibyte);
    
    WCHAR * *pWideChar = new WCHAR(nLen);
    memset(pWideChar, 0x00, (nLen)*sizeof(WCHAR));
 
    MultiByteToWideChar(CP_ACP, 0, (LPCSTR)pMultiByte, -1, pWideChar, nLen);
 
   CString strUnicode;
   strUnicode.format(_T("%s"), pWideChar);      // byte을 aligne해서 넣는다??
 
    delete [] pWideChar;
 
   return strUnicode;
}
 
wchar_t strUnicode[256]={0,};
char      strMultibyte[256]={0,};
strcpy_s( strMultibyte, 235, "멀티바이트");
int nLen = MultiByteToWideChar( CP_ACP, 0, strMultibyte, strlen(strMultibyte), NULL, NULL);
MultiByteToWideChar(CP_ACP, 0, strMultibyte, strlen(strMultibyte), strUnicode, nLen);
 
 
UTF-8 -> 유니코드
 
wchar_t strUnicode[256]={0,};
char      strUTF8[256]={0,};
strcpy_s( strUTF8, 256, "utf-8글자..");
int nLen = MultiByteToWideChar( CP_UTF8, 0, strUTF8, strlen(strUTF8), NULL, NULL);
MultiByteToWideChar( CP_UTF8, 0, strUTF8, strlen(strUTF8), strUnidcode, nLen);
 
 
 
 
 
#pragma once
#include <Windows.h>
#include <atlbase.h>
#include <iostream>
 
void func()
{
     USES_CONVERSION;  //매크로 선언
     
     LPCSTR        mChar;
     LPCWSTR     wChar = L"test";
 
    mChar = W2A( wChar );     //유니코드 문자열을 멀티바이트문자열로 변환
    wChar = A2W( mChar, CP_UTF8 );     //멀티바이트문자열을 유니코드문자열로 변환
 
}
 
 
 
 
 
인코딩(Encoding) - ASCII, ANSI, Multi-Byte, Unicode
 
아스키(ASCII)코드( 표)
    :: 128개문자
ANSI
    :: 영어만을 고려하여 만들어진 ASCII에서 다른 언어를 지원해야 할 필요가 생겨서...
    :: 아스키의 확장판 : 앞의 7bit(ASCII와 동일) + 1 bit(CodePage) = 총 8bit로 사용
             :::: CodePage = CP949, EUC-KR
    
 
 
한글처리
  :: EUK-KR ( Extended Unix Code-Korea)
         :::: 한글 지원을 위해 유닉스 계열에서 나온 '완성형' 코드 조합,  ANSI를 한국에서 확장한 것으로 외국에서는 지원이 안 될 가능성이 높다.
   :: CP949(Code Page 949)
         :::: 한글 지원을 위해 윈도우즈 계열에서 나온 확장 완성형 코드 
 
 
UTF-8
   1. 유니코드를 위한 가변길이 문자 인코딩(멀티바이트)방식...
   2. 처음 128글자는 ASCII코드값으로 동일
   3. 2bytes를 사용하여, 중동지역 언어 또는 많은 유럽 언어를 표현...
   4. 3byte를 사용하여 동아시아어권(한국,중국,일본..)
 
UTF-16
   1.  한글의 경우, UTF-8로 저정할 경우, 3바이트를 필요로 하므로,  UTF-16으로 저장하면 용량의 이점이 있음.
   2.  Endian 처리를 고려함에 따른 복잡성 증대나 ANSI와의 호환이 안되는 단점이 있음...
 
 
 
gcc 에서 characters
 
 
서버 프로그램에서 socker을 통해 전달받은 메시지 프로토콜은, 기본 인코딩은 유니코드임...(UString)...UTF-16 즉,, 2바이트 사용... 
   예시  
       //int n = ustrPassWord.Find( LPCWSTR(":MOD"));
       int n = ustrPassWord.Find( LPCWSTR("\x00\x3A\x00\x4D\x00\x4F\x00\x44\x00"));
 
   :: 유니코드에서 ->   멀티바이트로 변환
         ustrAccountName.FromMBC( CP_UTF8,   LPCSTR( g_theDoc.m_aryAuthAccountName.GetAt(i)) );    // MultiByte를  유니코드로 변환..)
 
 
   :: 멀티바이트에서 -> 유니코드로 변환
         mstrDebug.FromUnicode( CP_KOREAN,  LPCWSTR(ustrUserID));
 
 
클라이언트에서 서버로 보낼 때 인코딩은?  
   ::   프로젝트 속성에서  _UNICODE가 선언되어 있음..
   ::   CString이 기본 자료형임..
   ::   MString으로 변환하여, 일반적인 char* 또는 숫자 기반을 처리함...
   ::  "~~~ :ENC"를 보내고 있음...

 

728x90
반응형

+ Recent posts