Cette réponse donne un bel aperçu de haut niveau de l'optimisation des chaînes courtes (SSO). Cependant, j'aimerais savoir plus en détail comment cela fonctionne dans la pratique, en particulier dans l'implémentation libc ++:
Quelle doit être la longueur de la chaîne pour être éligible au SSO? Cela dépend-il de l'architecture cible?
Comment l'implémentation distingue-t-elle les chaînes courtes et longues lors de l'accès aux données de chaîne? Est-ce aussi simple
m_size <= 16
ou s'agit-il d'un indicateur faisant partie d'une autre variable membre? (J'imagine quem_size
ou une partie de celui-ci pourrait également être utilisé pour stocker des données de chaîne).
J'ai posé cette question spécifiquement pour libc ++ parce que je sais qu'il utilise SSO, cela est même mentionné sur la page d'accueil de libc ++ .
Voici quelques observations après avoir regardé la source :
libc ++ peut être compilée avec deux dispositions de mémoire légèrement différentes pour la classe string, ceci est régi par l' _LIBCPP_ALTERNATE_STRING_LAYOUT
indicateur. Les deux configurations distinguent également les machines petit-boutiste et grand-boutiste, ce qui nous laisse un total de 4 variantes différentes. Je vais supposer la mise en page "normale" et little-endian dans ce qui suit.
En supposant en outre que size_type
4 octets et value_type
1 octet, voici à quoi ressembleraient les 4 premiers octets d'une chaîne en mémoire:
// short string: (s)ize and 3 bytes of char (d)ata
sssssss0;dddddddd;dddddddd;dddddddd
^- is_long = 0
// long string: (c)apacity
ccccccc1;cccccccc;cccccccc;cccccccc
^- is_long = 1
Étant donné que la taille de la chaîne courte est dans les 7 bits supérieurs, elle doit être décalée lors de l'accès:
size_type __get_short_size() const {
return __r_.first().__s.__size_ >> 1;
}
De même, le getter et le setter pour la capacité d'une longue chaîne utilisent __long_mask
pour contourner le is_long
bit.
Je cherche toujours une réponse à ma première question, à savoir quelle valeur __min_cap
la capacité des chaînes courtes prendrait pour différentes architectures?
Autres implémentations de bibliothèques standard
Cette réponse donne un bon aperçu des std::string
dispositions de mémoire dans d'autres implémentations de bibliothèques standard.
string
tête ici , je le vérifie en ce moment :)