2011-12-12 38 views
1

以下是我如何使用字符串標記器。字符串標記器失敗

typedef std::string      string_t; 
typedef std::vector<string_t>   stations_t; 

void Tokenize(const string_t& str, stations_t& tokens,const string_t& delimiters = " ") { 
    string_t::size_type lastPos = str.find_first_not_of(delimiters, 0); 
    string_t::size_type pos  = str.find_first_of(delimiters, lastPos); 
    while (string_t::npos != pos || string_t::npos != lastPos){ 
     tokens.push_back(str.substr(lastPos, pos - lastPos)); 
     lastPos = str.find_first_not_of(delimiters, pos); 
     pos = str.find_first_of(delimiters, lastPos); 
    } 
} 

當我傳遞字符串1,8003,1,HWH,Kolkata Howrah Junction,,16:10,,1,0這一點,它返回我8領域,在那裏,它應該返回9,它是完全忽略,,一部分。任何人都可以看看,並幫助我找到這裏的錯誤。

回答

2

在你提供的例子中,你需要一個在「16:10」和「1」之間的空字段,對吧?

你沒有得到它的原因,是因爲當你得到子字符串「16:10」,那麼pos是43,並且你尋找一個字符不在從該位置開始的分隔字符串中。第一個非分隔符是「1」的位置45

我建議是這樣的:

void Tokenize2(const string_t& str, stations_t& tokens,const string_t& delimiters = " ") { 
    string_t::size_type elem_start = 0; 
    string_t::size_type elem_end = str.find_first_of(delimiters, 0); 
    while (elem_start != string_t::npos && elem_end != string_t::npos) { 
     tokens.push_back(str.substr(elem_start, elem_end - elem_start)); 
     elem_start = str.find_first_of(delimiters, elem_end) + 1; 
     elem_end = str.find_first_of(delimiters, elem_start); 
    } 

    if (elem_start != string_t::npos) { 
     // Get the last element 
     tokens.push_back(str.substr(elem_start, elem_end - elem_start)); 
    } 
} 
1

這個錯誤在於你找到一個令牌的邏輯。

lastPos = str.find_first_not_of(delimiters, 0); 
pos  = str.find_first_of(delimiters, lastPos); 

基本上你試圖找到一個字符不是一個分隔符,並將其分配給lastPos,這樣就可以進行後lastPos找到第一個分隔符,並將其分配給POS搶之間的一切lastPostpos是一個令牌。基本上,試圖找到find_first_not_of的行爲將跳過任何連續的分隔符。您可以使用測試輸入

,,,,,,,,22, 

,你會發現,第一次迭代找到令牌,並跳過所有 連續「」 S

How do I tokenize a string in C++?有很多的方式來寫一個標記