STL basic_string 长度(含空字符)
为什么您可以在 std::basic_string 中插入 '\0' 字符并且 .length() 方法不受影响,但如果您调用 char_traits
例如
string str("abcdefgh");
cout << str.length(); // 8
str[4] = '\0';
cout << str.length(); // 8
cout << char_traits<char>::length(str.c_str()); // 4
Why is it that you can insert a '\0' char in a std::basic_string and the .length() method is unaffected but if you call char_traits<char>::length(str.c_str())
you get the length of the string up until the first '\0' character?
e.g.
string str("abcdefgh");
cout << str.length(); // 8
str[4] = '\0';
cout << str.length(); // 8
cout << char_traits<char>::length(str.c_str()); // 4
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
好问题!
原因是 C 样式字符串被定义为以空字节结尾的字节序列。当您使用
.c_str()
从 C++std::string
中获取 C 样式字符串时,您将返回 C++ 字符串存储的序列其后有一个空字节。当您将其传递给strlen
时,它将扫描字节,直到遇到空字节,然后报告在此之前找到的字符数。如果string
包含空字节,则strlen
将报告一个小于字符串整个长度的值,因为它会在到达字符串的真正末尾之前停止。一个重要的细节是::eq(s[i], charT()) 为真。对于
strlen
和char_traits::length
不是同一个函数。但是,char_traits::length
(§21.1.1) 的 C++ ISO 规范规定char_traits::length(s)
返回 最小i
使得 char_traitschar_traits
,eq
函数仅通过执行==
比较来返回两个字符是否相等,并通过以下方式构造字符编写char()
会产生一个空字节,因此这相当于说“字符串中的第一个空字节在哪里?”这本质上就是strlen
的工作原理,尽管这两个函数在技术上是不同的。然而,C++
std::string
是“任意字符序列”的更通用概念。其实现的细节对外界是隐藏的,尽管它可能由开始和停止指针或指针和长度表示。由于这种表示形式不依赖于存储的字符,因此询问 std::string 的长度可以告诉您有多少个字符,而不管这些字符实际上是什么。希望这有帮助!
Great question!
The reason is that a C-style string is defined as a sequence of bytes that ends with a null byte. When you use
.c_str()
to get a C-style string out of a C++std::string
, then you're getting back the sequence the C++ string stores with a null byte after it. When you pass this intostrlen
, it will scan across the bytes until it hits a null byte, then report how many characters it found before that. If thestring
contains a null byte, thenstrlen
will report a value that's smaller than the whole length of the string, since it will stop before hitting the real end of the string.An important detail is that
strlen
andchar_traits<char>::length
are NOT the same function. However, the C++ ISO spec forchar_traits<charT>::length
(§21.1.1) says thatchar_traits<charT>::length(s)
returns the smallesti
such thatchar_traits<charT>::eq(s[i], charT())
is true. Forchar_traits<char>
, theeq
function just returns if the two characters are equal by doing a==
comparison, and constructing a character by writingchar()
produces a null byte, and so this is equal to saying "where is the first null byte in the string?" It's essentially howstrlen
works, though the two are technically different functions.A C++
std::string
, however, it a more general notion of "an arbitrary sequence of characters." The particulars of its implementation are hidden from the outside world, though it's probably represented either by a start and stop pointer or by a pointer and a length. Because this representation does not depend on what characters are being stored, asking thestd::string
for its length tells you how many characters are there, regardless of what those characters actually are.Hope this helps!