2009-08-09 21 views
11

He estado buscando boost :: tokenizer, y he encontrado que la documentación es muy delgada. ¿Es posible hacer que tokenize una cadena como "delfín - mono - babuino" y hacer que cada palabra sea un token, así como también cada doble un símbolo? De los ejemplos solo he visto delimitadores de caracteres individuales permitidos. ¿La biblioteca no está lo suficientemente avanzada para delimitadores más complicados?Usando boost :: tokenizer con delimitadores de cadena

+1

Sólo por curiosidad, por qué esto está marcado wiki de la comunidad? –

+0

Pensé que permitiría a otros aclarar mi pregunta en caso de que fuera un poco difusa. Tal vez debería leer sobre lo que es, hasta la próxima. – Martin

Respuesta

0

Parece que tendrá que escribir su propio TokenizerFunction para hacer lo que quiera.

+0

Ya veo. Esperaba que hubiera algo prefabricado, pero creo que esperaba demasiado. – Martin

1

Una opción es probar boost :: regex. No estoy seguro del rendimiento en comparación con un tokenizador personalizado.

std::string s = "dolphin--monkey--baboon"; 

boost::regex re("[a-z|A-Z]+|--"); 
boost::sregex_token_iterator iter(s.begin(), s.end() , re, 0); 
boost::sregex_token_iterator end_iter; 

while(iter != end_iter) 
{ 
    std::cout << *iter << '\n'; 
    ++iter; 
} 
+0

Esto es bueno. Si funciona, obtiene mi voto. :) –

10

usando iter_split le permite usar varios tokens de caracteres. El código siguiente produciría el siguiente:

delfines
mon-clave
babuino

#include <iostream> 
#include <boost/foreach.hpp> 
#include <boost/algorithm/string.hpp> 
#include <boost/algorithm/string/iter_find.hpp> 

    // code starts here 
    std::string s = "dolphin--mon-key--baboon"; 
    std::list<std::string> stringList; 
    boost::iter_split(stringList, s, boost::first_finder("--")); 

    BOOST_FOREACH(std::string token, stringList) 
    {  
     std::cout << token << '\n'; ; 
    } 
+1

Esto tiene el inconveniente de crear una copia de la cadena completa. Si la cadena que está siendo tokenizada es grande, esto es un problema. El tokenizador de refuerzo no hace esto. –

2

Sé que el tema es bastante antiguo, pero se muestra en los primeros eslabones de Google cuando búsqueda "impulsar tokenizer por cadena"

por lo que se sumará a mi variante de TokenizerFunction, por si acaso:

class FindStrTFunc 
{ 
public: 
    FindStrTFunc() : m_str(g_dataSeparator) 
    { 
    } 

    bool operator()(std::string::const_iterator& next, 
     const std::string::const_iterator& end, std::string& tok) const 
    { 
     if (next == end) 
     { 
      return false; 
     } 
     const std::string::const_iterator foundToken = 
      std::search(next, end, m_str.begin(), m_str.end()); 
     tok.assign(next, foundToken); 
     next = (foundToken == end) ? end : foundToken + m_str.size(); 
     return true; 
    } 

    void reset() 
    { 
    } 

private: 
    std::string m_str; 
}; 

después podemos crear

boost::tokenizer<FindStrTFunc> tok("some input...some other input"); 

y utilizar, como un impulso habitual tokenizer

+0

la implementación no es ideal (podría tener errores), es solo un ejemplo – Alek86

Cuestiones relacionadas