-
Notifications
You must be signed in to change notification settings - Fork 1
1.9 Trimming Blanks From the Ends of a String
s.erase(std::find_if(s.rbegin(), s.rend(), [](int c) { return !std::isspace(c); }).base(), s.end());
Understanding how this works can be instructive so let's go though it step by step. The above statement operates in-place on a standard string removing any trailing space. Since we know we are removing stuff we know it will take the form of:
s.erase( .... )
The erase method takes a begin and end iterator to define what, if anything, will be erased. Since we are trimming from the end of the string we know that it will take the form of:
s.erase( .... , s.end() );
We need to find where non-space characters start. To that we can use the find_if algorithm.
s.erase( find_if( .... ), s.end() );
find_if
takes three arguments, a begin iterator, end iterator, and conditional. It returns the position where the predicate was true. Since we are trimming the end of the string, we use the reverse
iterators. However, this will make find_if return a reverse iterator, which is not what we want. We can get the forward iterator by calling .base on the returned reverse iterator.
s.erase ( find_if(s.rbegin(), s.rend(), ....).base(), s.end() );
Finally we can provide a lambda method that returns true as soon as a non-space character is found:
[](int c) { return !std::isspace(c); }
Putting it all together we have:
s.erase(std::find_if(s.rbegin(), s.rend(), [](int c) { return !std::isspace(c); }).base(), s.end());
We might want to wrap this in a convenient method like:
std::string& rtrim(std::string &s)
{
s.erase(std::find_if(s.rbegin(), s.rend(), [](int c) {return !std::isspace(c);}).base(), s.end());
return s;
}
This way we can simply call rtrim("Hello world ")
and the tailing space will be trimmed from the string.
#include <boost/algorithm/string/trim.hpp>
boost::trim_right(s);
There are an assortment of trim algorithms built available in boost.