gpt4 book ai didi

c++ - 这是使用 c_str 异常未定义行为吗?

转载 作者:太空狗 更新时间:2023-10-29 20:02:11 26 4
gpt4 key购买 nike

我见过几个类似的代码片段,如下所示:

struct MyExcept : std::exception {
explicit MyExcept(const char* m) noexcept : message{m} {}

const char* what() const noexcept override {
return message;
}

const char* message;
};

void foo() {
std::string error;

error += "Some";
error += " Error";

throw MyExcept{error.c_str()};
}

int main() {
try {
foo();
} catch (const MyExcept& e) {
// Is this okay?
std::cout << e.message << std::endl;
}
}

在注释 Is this okay? 之后的行中,我们使用 std::string 读取了在 foo 函数中分配的 c 风格字符串。由于字符串随着堆栈展开而被破坏,这是未定义的行为吗?


如果它确实是未定义的行为,如果我们用这个替换 main 函数呢?

int main() {
foo();
}

因为没有 catch,编译器不会被迫展开堆栈,而是在控制台输出 what() 的结果并中止程序。那么它仍然是未定义的行为吗?

最佳答案

是的,这是未定义的行为。您正在使用悬空指针。

void foo() {
std::string error;

error += "Some";
error += " Error";

throw MyExcept{error.c_str()};
} // << error goes out of scope here and so does the pointer returned
// from c_str()

Since there is no catch, the compiler is not forced to unwind the stack, and yet output the result of what() in the console and abort the program. So is it still undefined behavior?

因为默认实现将使用 std::terminate并依次调用 std::abort() 这可能仍然是未定义的行为,因为大多数标准处理程序实现将尝试取消引用 what()

不过,您可以安装自己的处理程序来避免这种情况。

关于c++ - 这是使用 c_str 异常未定义行为吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/45220063/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com