The only way to legally make modifications to a std::string is through
it's member functions (including the access paths they indirectly
provide). Thus, you should rewrite your removeDup to take
std::string::iterator as arguments, something like:
std::string
removeDup( std::string& original )
{
std::string::iterator current = original.begin();
std::string::iterator end = original.end();
while ( current != end ) {
end = std::remove( current + 1, end, *current );
++ current;
}
original.erase( end, original.end() );
return original;
}
(I think this does what your original code does. I can't be sure,
because I couldn't really figure out your original code.)
From a design point of view, this is ugly; you should probably pass a
std::string const&, and return a new std::string:
std::string
removeDup( std::string const& original )
{
std::string results;
std::bitset<UCHAR_MAX + 1> alreadySeen;
for ( std::string::const_iterator current = original.begin();
current != original.end();
++ current ) {
if (! alreadySeen.test( static_cast<unsigned char>( *current ) ) ) {
results += *current;
alreadySeen.set( static_cast<unsigned char>( *current ));
}
}
return results;
}
The only time you want to get a char* from a std::string is to pass
it to legacy code (or C). In such cases, std::string::c_str() is the
approved method; if the function you are calling requires a char*,
then:
if the function doesn't actually modify the string (it's not const
correct, but this is the case for many C functions), then use
const_cast on the return value of std::string::c_str(), otherwise
you must allocate a local buffer, and pass it:
std::vector localBuffer( s.begin(), s.end() );
localBuffer.push_back( '\0' );
legacyFunction( &localBuffer[0], localBuffer.size() );
stringinstead and skipchar*completely