在这个初始化过程中创建了多少临时对象?
Posted
技术标签:
【中文标题】在这个初始化过程中创建了多少临时对象?【英文标题】:How many temporary objects are created in this initialization? 【发布时间】:2019-04-26 12:19:49 【问题描述】:我有这个初始化:
const char* str = std::string("a").c_str();
本次初始化创建了多少临时对象?
"a"
可以被视为临时工吗?对象?
我知道std::string("a")
是临时工。对象。
c_str()
的结果是一个对象,str
存储它。所以这不是临时工。对象,对吧?
【问题讨论】:
临时的std::string
是唯一的临时对象,而str
是这个之后的悬空指针
我认为指针是对象。
@JoãoPaulo 他们是。但是,作为纯右值,初始化程序被具体化为 str
,没有临时对象。在 C++17 之前有一个
看起来像纯右值are no longer materialized。
@wally 谢谢沃利。不过,我对这个词有点怀念。
【参考方案1】:
"a"
是const char[2]
类型的字符串字面量,所以它是一个对象。
std::string("a")
是一个纯右值表达式并且不是一个临时对象(目前)。当您调用c_str()
时,您会具体化一个临时对象并在其上调用c_str()
,以获取指向临时对象数据的指针。
然后您将指针的地址分配给str
,所以现在str
将地址保存到指向临时对象数据的指针。在该完整表达式的末尾,物化临时对象被销毁,使对该临时数据的迭代器/指针/引用无效。
这意味着str
现在指向您不再拥有的内存,称为悬空指针。除了给它分配一个不同的地址之外,对它做任何事情都是未定义的行为。
所以当一切都结束时,你有 2 个对象。一个悬空指针 (str
) 和一个字符串字面量 ("a"
)。
【讨论】:
【参考方案2】:只有一个。字符串。
"a"
是一个字面量,它的类型是const char[]
,大小合适,它有一个静态存储。所以,这肯定不是暂时的。
str
,返回值c_str()
也是const char
指针。
没有创建其他对象。
【讨论】:
"a" 是一个字面量,以const char*
表示。所以它不能被认为是一个对象。 这是错误的。字符串字面量是一个左值const char[N]
数组,所以它是一个对象。
@JoãoPaulo 不会。它将在程序的整个生命周期内一直存在。
@luk32 它被标准明确称为一:timsong-cpp.github.io/cppwp/lex.string#15
@curiousguy 什么?该标准说对象具有静态存储持续时间,从上面指定的给定字符初始化。所以它有一个定义的生命周期(静态对象从它们第一次遇到到程序结束)并且它被初始化。
@curiousguy 抱歉,这是完全错误的。如果你愿意,你可以问一个 Q 并得到一个明确的答案。如果使用字符串文字是 UB,那么基本上所有程序都是 UB。字符串字面量是对象的定义,对象的生命周期在第一次遇到字符串字面量时开始。【参考方案3】:
"a"
可以被视为临时工吗?对象?
从技术上讲,定义不明确。
它确实没有有一个定义的生命周期。从技术上讲,使用它不已经定义了行为。 不是正式开始对象生命周期的构造。
实际上你可以使用它(显然)。
【讨论】:
对不起所有的反对者,这是真的; std 中没有任何内容表明"a"
的生命周期开始了。没有。字面意思,就是使用字符串句号是UB。以上是关于在这个初始化过程中创建了多少临时对象?的主要内容,如果未能解决你的问题,请参考以下文章