E D R S I H C RSS
ID
Password
Join
한 드럼의 조심성은 한 파운드의 지혜와 맞먹는다. -독일속담

간단한 파싱처리를 해야하는데, 막상 문자열 일일히 비교하기란 귀찮기 짝이 없는 작업입니다. 이를 실행하기 위한 몇가지 방법들을 찾아보았습니다.

strtok() #

표준 C 함수인데다가 쓰기도 쉽습니다. 가장 무난하지만 다음과 같은 단점이 있습니다.
  • strtok() 파싱중에 다시 strtok()을 호출하면 파싱이 엉클어지더군요. (아무래도 내부 버퍼를 공유해서 생기는 버그인듯)
  • c 함수인지라 매번 char[] 배열을 선언해주어야합니다.
  • 파싱대상이 되는 char * 배열의 내용을 수정하므로 DLL 함수와 같은데서 반환한 const char *에 strtok()을 실행하면 보호오류가 발생하더군요.

boost::tokenizer #

boost를 사용한다면 같이 활용할 수 있는 라이브러리인데 다음과 같은 단점이 있습니다.
  • 당연하지만 boost가 필요합니다! 간단한 프로젝트에는 적용하는데 귀차니즘을 불러일으킬 수도...
  • 간혹 첫번째 토큰을 분석못하는 버그가 있습니다. (이때문에 사용하지 않고 있습니다)
  • 템플릿 기반이라 실행화일 용량을 크게 만듭니다.

Tokenize #

[http]http://linuxselfhelp.com/HOWTO/C++Programming-HOWTO-7.html에서 우연히 발견한 루틴입니다. 꽤 깔끔하고 뭐니뭐니해도 표준 C++ 기반이라 별도의 라이브러리도 필요없습니다. :) 가장 좋은 방법으로 생각합니다. 아래 함수를 선언해놓고 감사히 사용합니다. :)
void Tokenize(const string& str, vector<string>& tokens, const string& delimiters = " ")
{
    // 처음에 나와있는 구분자들을 건너뜁니다.
    string::size_type lastPos = str.find_first_not_of(delimiters, 0);
    // 첫번째 "구분자가 아닌 문자"를 찾습니다.
    string::size_type pos     = str.find_first_of(delimiters, lastPos);

    while (string::npos != pos || string::npos != lastPos)
    {
        // 토큰을 찾았으면 이것을 vector에 추가합니다.
        tokens.push_back(str.substr(lastPos, pos - lastPos));
        // 구분자를 건너뜁니다. "not_of"에 주목하세요.
        lastPos = str.find_first_not_of(delimiters, pos);
        // 그다음 "구분자가 아닌 문자"를 찾습니다.
        pos = str.find_first_of(delimiters, lastPos);
    }
}

Valid XHTML 1.0! Valid CSS! powered by MoniWiki
last modified 2010-10-28 12:42:52
Processing time 0.3403 sec