L'"histoire" est la suivante : il y a longtemps, lorsque tout le monde travaillait dans des threads uniques, ou du moins lorsque les threads étaient des travailleurs avec leurs propres données, ils ont conçu une classe de chaîne pour C++ qui rendait la manipulation des chaînes plus facile qu'auparavant, et ils ont surchargé l'opérateur+ pour concaténer les chaînes.
Le problème était que les utilisateurs faisaient quelque chose comme :
s = s1 + s2 + s3 + s4;
et chaque concaténation créait un temporaire qui devait implémenter une chaîne de caractères.
C'est pourquoi quelqu'un a eu l'idée d'une "évaluation paresseuse", de sorte qu'en interne, vous pourriez stocker une sorte de "corde" avec toutes les chaînes jusqu'à ce que quelqu'un veuille les lire comme des chaînes C, auquel cas vous changeriez la représentation interne en un tampon contigu.
Cela a résolu le problème ci-dessus mais a causé un tas d'autres maux de tête, en particulier dans le monde multithread où l'on s'attendait à ce qu'une opération .c_str() soit en lecture seule / ne change rien et donc pas besoin de verrouiller quoi que ce soit. Le verrouillage interne prématuré dans l'implémentation de la classe juste au cas où quelqu'un le ferait en multithread (alors qu'il n'y avait même pas de standard de threading) n'était pas non plus une bonne idée. En fait, il était plus coûteux de faire quelque chose de ce genre que de simplement copier le tampon à chaque fois. La même raison pour laquelle l'implémentation "copy on write" a été abandonnée pour les implémentations de chaînes de caractères.
Faisant ainsi .c_str()
Une opération véritablement immuable s'est avérée être la chose la plus sensée à faire, mais pouvait-on s'y fier dans une norme qui tient compte des threads ? La nouvelle norme a donc décidé d'indiquer clairement que c'est possible et que la représentation interne doit donc contenir le terminateur nul.