Manera correcta de dividir un std::string en un vector<string>
¿Cuál es la forma correcta de dividir una cadena en un vector de cadenas? El delimitador es un espacio o una coma.
Aceptado
Una forma conveniente sería la biblioteca de algoritmos de cadenas de Boost .
#include <boost/algorithm/string/classification.hpp> // Include boost::for is_any_of
#include <boost/algorithm/string/split.hpp> // Include for boost::split
// ...
std::vector<std::string> words;
std::string s;
boost::split(words, s, boost::is_any_of(", "), boost::token_compress_on);
Para cadenas separadas por espacios, puede hacer esto:
std::string s = "What is the right way to split a string into a vector of strings";
std::stringstream ss(s);
std::istream_iterator<std::string> begin(ss);
std::istream_iterator<std::string> end;
std::vector<std::string> vstrings(begin, end);
std::copy(vstrings.begin(), vstrings.end(), std::ostream_iterator<std::string>(std::cout, "\n"));
Producción:
What
is
the
right
way
to
split
a
string
into
a
vector
of
strings
cadena que tiene coma y espacio
struct tokens: std::ctype<char>
{
tokens(): std::ctype<char>(get_table()) {}
static std::ctype_base::mask const* get_table()
{
typedef std::ctype<char> cctype;
static const cctype::mask *const_rc= cctype::classic_table();
static cctype::mask rc[cctype::table_size];
std::memcpy(rc, const_rc, cctype::table_size * sizeof(cctype::mask));
rc[','] = std::ctype_base::space;
rc[' '] = std::ctype_base::space;
return &rc[0];
}
};
std::string s = "right way, wrong way, correct way";
std::stringstream ss(s);
ss.imbue(std::locale(std::locale(), new tokens()));
std::istream_iterator<std::string> begin(ss);
std::istream_iterator<std::string> end;
std::vector<std::string> vstrings(begin, end);
std::copy(vstrings.begin(), vstrings.end(), std::ostream_iterator<std::string>(std::cout, "\n"));
Producción:
right
way
wrong
way
correct
way
Puedes usar getline con delimitador:
string s, tmp;
stringstream ss(s);
vector<string> words;
while(getline(ss, tmp, ',')){
words.push_back(tmp);
.....
}
vector<string> split(string str, string token){
vector<string>result;
while(str.size()){
int index = str.find(token);
if(index!=string::npos){
result.push_back(str.substr(0,index));
str = str.substr(index+token.size());
if(str.size()==0)result.push_back(str);
}else{
result.push_back(str);
str = "";
}
}
return result;
}
dividir("1,2,3",",") ==> ["1","2","3"]
dividir("1,2,",",") ==> ["1","2",""]
dividir("1token2token3","token") ==> ["1","2","3"]