web-dev-qa-db-fra.com

Pourquoi `std :: stringstream :: stringstream (std :: string &&)` n'existe-t-il pas?

J'espérais que stringstream a un constructeur qui vole son contenu initial à un string&&. Ces "constructeurs de mouvements" inter-espèces n'existent-ils généralement pas dans la STL? Sinon, pourquoi pas?

48
Museful

Il y a l'histoire, ce qui est décevant. Mais aussi un avenir prometteur.

Lorsque la sémantique des mouvements est entrée dans C++ 11, c'était énorme, controversé et écrasant. Je voulais pouvoir déplacer des chaînes dans et hors de stringstream. Cependant, la politique de l'époque exigeait que le magasin interne n'ait pas pour être un basic_string<charT>. Par exemple, le magasin interne pourrait être un vector. Et il n'y avait aucune possibilité de contrôler les choses avec un allocateur. En tout état de cause, le besoin a été reconnu dans le délai C++ 11, mais ce n'était qu'un pont trop loin.

Heureusement, Peter Sommerlad a pris le relais avec P0408 . Cette proposition ajoute la fonctionnalité que vous recherchez, espérons-le pour C++ 20, mais ce n'est pas encore certain. Il est passé avec succès par le LEWG et est actuellement sur le bureau du LWG. Ils n'y sont pas parvenus ce mois-ci à Rapperswil, uniquement à cause d'un horaire surchargé. J'espère qu'il passera par le LWG et que le vote du comité sera complet. Il aura certainement mon vote.

55
Howard Hinnant

Pourquoi std::stringstream::stringstream(std::string&&) n'existe-t-il pas?

Cela est dû au tampon interne de std::stringstream , rdbuf .

rdbuf, (type std::string_buf ), ne prend pas en charge non-copie accès selon la motivation dans la proposition, p0408r4 :

... il n'y a pas non-copie accès au tampon interne d'un basic_stringbuf qui rend au moins l'obtention des résultats de sortie d'un ostringstream inefficace, car une copie est toujours effectuée

Cependant, il existe déjà un plan pour supporter le déplacement de std::string Dans le constructeur de stringsteam:

explicit basic_ostringstream(
   basic_string<charT, traits, Allocator>&& str,
   ios_base::openmode which = ios_base::out,
   const Allocator& a = Allocator());

ET déplacez str()

template<class SAlloc = Allocator>
void str(basic_string<charT, traits, SAlloc>&& s);
12
Joseph D.