简体   繁体   English

为什么std :: string不提供到const char *的转换?

[英]Why does std::string not provide a conversion to const char*?

This is more of a policy or a historical question. 这更多是一个政策或历史问题。 Why was it decided not to provide a const char * conversion for std::string? 为什么决定为std :: string提供const char *转换? Were there a fear someone might do printf("%s", s) and believe it would automatically convert? 是否担心有人会执行printf(“%s”,s)并认为它会自动转换? Are there any open discussions on this issue? 关于这个问题有公开的讨论吗?

Automatic casts are almost always evil. 自动强制转换几乎总是邪恶的。 If there were a cast to const char * , a std::string could be also automatically cast to other pointer types and that could lead to hard to find bugs. 如果对const char *进行了强制类型转换,则std::string也会自动强制转换为其他指针类型,这可能导致难以发现错误。 There is the c_str() method that returns const char * so you can still achieve what you need. 有一个c_str()方法返回const char *因此您仍然可以实现所需的功能。 Also, the typecast is not logically correct - std::string is not equivalent to const char * . 另外,类型转换在逻辑上也不正确std::string不等同于const char *

The string class internally need not store the string with a terminating 0. In fact it doesn't even have to store them in contiguous memory if it didn't want to. 字符串类在内部不必存储以0结尾的字符串。实际上,如果不想,它甚至不必将它们存储在连续的内存中。 Therefore an implicit cast doesn't make sense, since it may be a costly operation. 因此,隐式强制转换是没有意义的,因为它可能是一项昂贵的操作。

The c_str() function then gives you the c-string. 然后,c_str()函数为您提供c字符串。 Depending on how the library stores it internally this function may have to create a temporary. 根据库内部存储方式的不同,此功能可能必须创建一个临时库。 This temporary is only valid until you modify the string. 该临时选项仅在您修改字符串之前有效。

It is unfortunately however since a string could just been specified to be a c-string internally. 但是不幸的是,因为在内部只能将字符串指定为c字符串。 This wouldn't lead to any loss of functionality and would allow an implicit conversion. 这不会导致任何功能损失,并且可以进行隐式转换。

Edit The standard does basically imply the memory is contiguous (if accessed through data() or the [] operator), though it need not be internally, and certainly not null terminated. 编辑该标准确实暗示着内存是连续的(如果通过data()或[]运算符访问),尽管它不一定是内部的,并且肯定不是null终止的。 Likely all implementations store the 0 as well. 可能所有实现也都存储0。 If this were standardized then the implicit conversion could be safely defined. 如果对此进行了标准化,则可以安全地定义隐式转换。

Regarding your previous comments: 关于您之前的评论:

If they are equivalent then there is no difference (except for convenience) to use cast instead of the c_str() call 如果它们是等效的,那么使用cast而不是c_str()调用没有区别(为方便起见)

There is one very important difference: one is implicit whereas the other is explicit. 有一个非常重要的区别:一个是隐式的,另一个是显式的。

C++0x introduces the notion of explicit cast operators, but until then they are implicit, meaning that it is never clear (when looking at the code) whether they will be used or not. C ++ 0x引入了explicit强制转换运算符的概念,但在此之前它们是隐式的,这意味着(在查看代码时)永远不会清楚是否会使用它们。

Implicit cast are bad, especially since they can be cascaded, leading to extremely obscure code. 隐式强制转换是不好的,尤其是因为它们可以级​​联,从而导致代码非常晦涩。

Moreover, as already stated, there is here a problem of correctness. 此外,如上所述,这里存在正确性的问题。 Because the pointer returned by c_str is only valid as long as the string object does not change, then you could find yourself with hard to find bugs. 因为c_str返回的指针仅在string对象不变的情况下才有效,所以您可能很难发现bug。 Consider: 考虑:

void function()
{
  std::map<int, char const*> map;

  map[1] = boost::lexical_cast<std::string>(47);

  std::cout << map[1] << std::endl; // CRASH here, if lucky...
}

My feeling is that C++ is a strongly typed language and implicit type conversions break type-safety. 我的感觉是C ++是一种强类型语言,隐式类型转换破坏了类型安全性。

It can often bite you where the conversion happens at a point where you do not expect it and can make your code hard to debug. 它通常会咬住转换发生的位置,而这是您不期望的,并且会使您的代码难以调试。

Non-explicit constructors can have a similar effect and std::string itself does have an implicit constructor from const char *. 非显式构造函数可以具有类似的效果,并且std :: string本身确实具有const char *的隐式构造函数。 In this case it is not necessarily a bad thing although it can lead to inefficient code. 在这种情况下,虽然它可能导致代码效率低下,但不一定是一件坏事。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM