为什么 C++ 流将布尔值视为数字?

Why do C++ streams treat bools as numerics?

在 C++ 中,当您输出 bool 时,流 I/O 库默认不会打印“true”或“false”,而是打印“1”或“0”。相反,需要通过 std::boolalpha/std::noboolalpha:

明确请求基于字的打印
#include <iostream>

int main()
{
    std::cout << bool{ false }; //Prints "0"
    std::cout << std::boolalpha; //Print all bools with alphanumerics
    std::cout << bool{ false }; //Prints "false"
    std::cout << std::noboolalpha; //Return to default
}

撇开这作为默认值是否合适(这对初学者来说肯定会造成混淆),我完全不确定为什么 C++ 提供 bool-as-numeric 功能。我能想到的一些似是而非的理由:

无论如何,我在网上找不到实际(历史)原因;例如,该主题从未在 C++FAQ 中提及。所以:为什么 C++ 在其 input/output 流中提供这种 bool-as-numeric 功能?

std::cout << bool{b} 使用 std::use_facet<std::num_put<char>>(std::cout.getloc()).put(std::cout, std::cout, std::cout.fill(), bool{b}) 进行实际输出。

这基本上是制作一个 printf 说明符并打印它(由标志修改)。

这是猜测,但可能是因为在 C++98 中,当它最初被标准化时(可能在准标准 C++ 中),C 中的布尔类型是 int,所以 printf("%d", 0 == 0); 输出 1。 (这仍然是 _Bool 提升为 int 的情况)。所以 C++ 希望在这种特定情况下将 bools 视为数字类型(特别是因为它使用了语言环境的 numeric 方面),并且只使用 [= 的 printf 说明符18=],以匹配相应 C 代码中的输出。

请注意 std::cout << std::setfill('0') << std::setw(5) << true; 输出 00001(可能甚至 commas/spaces/full 也会停止,具体取决于语言环境)。没有 std::boolalphastd::cout << bool{b} 从字面上等同于 std::cout << static_cast<int>(bool{b}),就像 C 可变参数提升一样。

此外,通过修改语言环境的 std::numpunct 方面并覆盖 std::numpunct<CharT>::do_truename and do_falsename 可获得本地化支持。但这与默认行为是否应为 std::boolalpha.

是正交的