PDA

View Full Version : Basic <algorithm> (reverse_copy) doesn't work with QString



AnthonyL
27th August 2016, 16:43
Following code returns empty string, why?


QString reverseQString( const QString & str )
{
QString rev;
reverse_copy( str.begin(), str.end(), rev.begin() );
return rev;
}


Added after 27 minutes:

Is the problem that reverse_copy in fact needs functionality of std::back_inserter, not just an iterator?

ars
27th August 2016, 16:52
Hello,

the local object rev is an empty string. std::reverse_copy expects that the destination container (in your case rev) already has allocated memory to store the reverse copy. To achieve this, add

rev.resize(str.size());
before calling reverse_copy.

See also http://www.cplusplus.com/reference/algorithm/reverse_copy/
Best regards
ars

anda_skoa
27th August 2016, 16:54
My guess would be that QString::begin() returns QString::end() when called on a null QString and one cannot assign to end().
I.e. QString::begin() of a null QString might not qualify as an OutputIterator.

You could try with a std::back_inserter.

Cheers,
_

AnthonyL
27th August 2016, 17:08
Hello,

the local object rev is an empty string. std::reverse_copy expects that the destination container (in your case rev) already has allocated memory to store the reverse copy. To achieve this, add

rev.resize(str.size());
before calling reverse_copy.

See also http://www.cplusplus.com/reference/algorithm/reverse_copy/
Best regards
ars

It then works, thanks

ars
27th August 2016, 17:22
Using std::back_inserter makes use of a sequence of QString::push_back() calls, which result in multiple memory reallocations (depending on the memory allocation strategy implemented in QString::push_back()). In the scenario posted by OP we already know the size of the result, so I expect better performance using a single memory reallocation than a sequence of reallocations. Of course this will not give measurable differences for small containers/strings.

Best regards
ars