临时函数调用:UB?
Temporary in a function call: UB?
考虑以下代码,基于this answer:
#include <iostream>
#include <sstream>
class StringBuilder {
public:
template <typename T> inline StringBuilder &operator<<(T const &t) {
ss << t;
return *this;
}
inline char const * c_str() {
return ss.str().c_str();
}
private:
std::stringstream ss;
};
void foo(const char *x) {
std::cout << x << std::endl;
}
int main() {
foo((StringBuilder() << "testing " << 12 << 3 << 4).c_str());
return 0;
}
使用临时 StringBuilder
的 return 值调用 foo()
是否会以任何方式导致 UB?
我问的原因是上面的例子很好用,但在现实生活中我使用的库除其他外还包含日志记录工具,使用这个库我会得到不正确的输出 (日志记录功能正确地接受了我的 char*
但在内部覆盖了它,这让我相信内存不再有效。
是的,但不是因为你的想法。
函数调用中的临时StringBuilder
直到foo
returns后才被销毁,所以没问题。
但是c_str()
方法returns调用.str().c_str()
的结果,而这个str()
返回的临时字符串被销毁为StringBuilder::c_str()
returns,意思是返回的指针在外面是无效的。使用此指针会导致 UB。
考虑以下代码,基于this answer:
#include <iostream>
#include <sstream>
class StringBuilder {
public:
template <typename T> inline StringBuilder &operator<<(T const &t) {
ss << t;
return *this;
}
inline char const * c_str() {
return ss.str().c_str();
}
private:
std::stringstream ss;
};
void foo(const char *x) {
std::cout << x << std::endl;
}
int main() {
foo((StringBuilder() << "testing " << 12 << 3 << 4).c_str());
return 0;
}
使用临时 StringBuilder
的 return 值调用 foo()
是否会以任何方式导致 UB?
我问的原因是上面的例子很好用,但在现实生活中我使用的库除其他外还包含日志记录工具,使用这个库我会得到不正确的输出 (日志记录功能正确地接受了我的 char*
但在内部覆盖了它,这让我相信内存不再有效。
是的,但不是因为你的想法。
函数调用中的临时StringBuilder
直到foo
returns后才被销毁,所以没问题。
但是c_str()
方法returns调用.str().c_str()
的结果,而这个str()
返回的临时字符串被销毁为StringBuilder::c_str()
returns,意思是返回的指针在外面是无效的。使用此指针会导致 UB。