为什么语句中的链接方法无法给出预期的结果?

Why does chaining methods in a statement fail to give an expected result?

本文关键字:结果 语句 链接 方法 为什么      更新时间:2023-10-16

我可以像这样计算std::filesystem::path变量的const char*表示:

std::filesystem::path path1(L"ConsoleApplication1.cpp");
std::string strPath1 = path1.string();
const char* charArrPath1 = strPath1.c_str();

但是如果我省略string变量的显式赋值并在 char 数组初始化语句中使用方法链

const char* charArrPath1 = path1.string().c_str();

变量charArrPath1在执行后包含垃圾。

为什么方法链似乎不起作用?

PS 如果我在初始化charArrPath1后将path1string()的结果显式分配给一些不相关的变量,我确实得到了预期的结果:

std::filesystem::path path1(L"ConsoleApplication1.cpp");
const char* charArrPath1 = path1.string().c_str();
std::string strPathUnrelated = path1.string();
std::cout << charArrPath1 << std::endl;

埃皮莱戈农:

当代码在 x86 配置(调试和发布(中运行时,方法链接似乎失败。在 x64 发布配置中运行时,以下程序

#include <iostream>
#include <filesystem>
int main()
{
std::filesystem::path path1(L"ConsoleApplication1.cpp");
const char* charArrPath1 = path1.string().c_str();
std::cout << charArrPath1 << std::endl;
}

打印输出

ConsoleApplication1.cpp

有人对这种行为有解释吗?

因为std::filesystem::path::string返回 by-value,所以它返回的是一个临时的,在完整的表达式之后会被销毁,让指针从c_str()晃来晃去。

正如您尝试的那样,如果您使用命名变量,指针将不会悬空,该变量不会立即销毁。

"悬空指针是依赖指针和显式释放资源的语言最黑暗的噩梦"(摘自Bjarne Stroustrup和Herb Sutter的"C++类型和资源安全模型简介",第3节。内存安全,第 4 页(

追逐我相当大的程序的一个看似间歇性的错误,我最终发现它是蛮力的,迭代断点。它碰巧隐藏在相当模糊的行中,这些行在很少执行的分支中构造文件系统路径提示。我想知道为什么"代码分析",一个很棒的工具,可以强制你的代码的类型和资源安全,你在Visual Studio的项目属性中启动检查"在构建时启用代码分析",未能警告我这些行,并发布了一个谨慎的问题到堆栈溢出,希望有人教我使用代码分析。

出于好奇,我还开始浏览 MSDN 文档,并了解到Microsoft本机建议规则集(C++项目的默认设置(不包含整个C++核心准则集。我选择了"所有规则"规则集Microsoft,针对旧版本的程序运行它,它标记了带有警告的罪魁祸首行 C26486 不要将可能无效的指针传递给函数。

至于我问题的 PS 和"Epilegomenon"部分,我发现不同配置的报告行为仅对 v142 平台工具集有效,并且(可能(意义不大。