代码之家  ›  专栏  ›  技术社区  ›  kdog

为什么std::string不接受空指针?

  •  8
  • kdog  · 技术社区  · 7 年前

    我最近向 std::string 构造函数,并获得未定义的行为。我敢肯定,这是成千上万的程序员在我之前做过的事情,同样的错误无疑使无数的程序崩溃。当使用 char* 使用编写代码的步骤 标准::字符串 ,这是一种在编译时无法捕获的东西,在运行时单元测试中很容易错过。

    我感到困惑的是,为什么要指定 标准::字符串 这边

    为什么不定义 std::string(NULL)=="" ?

    效率损失可以忽略不计,我怀疑它在实际项目中是否可以测量。

    有人知道 std::string(NULL) 未定义is?

    2 回复  |  直到 7 年前
        1
  •  8
  •   Yakk - Adam Nevraumont    7 年前

    据我所知,没有什么好的理由。

    有人提议对此进行更改 a month ago . 我鼓励你支持它。

    std::string 不是很好的标准化的最好例子。最初标准化的版本无法实施;对其提出的要求彼此不一致。

    在某种程度上,不一致性得到了修复。

    在里面 更改的规则阻止了COW(写时拷贝)实现,这打破了现有合理兼容的ABI 标准::字符串 s、 我想不起来,这种变化可能是不一致性得到修复的地方。

    它的API不同于 std 的容器,因为它不是来自同一个pre- 标准 STL。

    处理以下遗留行为 标准::字符串 因为考虑到性能成本的某种合理决策是不现实的。如果做过这样的测试,那是20多年前的一次非标准测试 标准::字符串 (因为不可能存在,标准不一致)。

    传球时仍然是UB (char const*)0 nullptr 由于 缺乏活力 ,并将继续这样做,直到有人提出建议,证明成本很小,而收益却很小。

    构建 标准::字符串 从文字 char const[N] 已经是低性能的解决方案;您在编译时已经知道了字符串的大小,将其放在地上,然后在运行时遍历缓冲区以找到 '\0' 字符(除非周围进行了优化;如果是这样,空检查同样可以优化)。高性能解决方案包括了解长度和讲述 标准::字符串 而不是从 '\0' 终止的缓冲区。

        2
  •  3
  •   Johannes Overmann    7 年前

    唯一原因是: 运行时性能。

    这确实很容易定义 std::string(NULL) 结果为空字符串。但在每一个 std::string 来自 const char * ,可以相加。

    在绝对最大性能和方便性之间的平衡上,C++总是追求绝对最大性能,即使这意味着会损害程序的健壮性。

    最著名的例子是默认情况下不初始化类中的POD成员变量:尽管在99%的情况下程序员希望初始化所有POD成员变量,但C++决定不这样做,以允许所有类中的1%实现略高的运行时性能。这种模式在C++中到处重复。性能胜过一切。

    C++中没有“性能影响可以忽略不计”。:-)

    (请注意,我个人也不喜欢C++中的这种行为 违约 行为是 安全 ,并且必须显式请求未经检查和未初始化的行为,例如使用额外的关键字。2018年,在许多项目中,未初始化变量仍然是一个主要问题。)