为什么 std::literals 运算符在包含对应的 header 时不会自动导出?
Why does std::literals operators not automatically export when include their correspond header?
在std::literals
命名空间中有一些字面运算符和它们对应的header如operator""s
、operator""sv
等
我想知道为什么这些运算符在包含相应的 header 时不会自动导出,因为它们不会相互冲突或 user-defined 必须以下划线开头的文字运算符,通常像我这样的用户想要在包含 header.
时使用它们
如果 using std::string_literals::operator""s;
已经在 <string>
header 以及其他库中,那就太好了:
#include <string> // automatically export the literal operators
#include <chrono> // automatically export the literal operators
int main() {
auto str = "hello world"s;
auto sec = 10s;
}
我看不出有什么坏处。为什么委员会不喜欢这样?它有什么问题或者这是一种不好的做法吗?
在 C++ 中,using
声明 无法 撤消。一旦它在那里,它后面的每一段代码(在它的范围内)都会有它的名称查找规则受该指令的影响。因此,全局 using
语句有些危险。它在 header 中更加危险,因为这将固有地影响包含 header(包括任何 header 的每个文件的行为在 之后 header).
因此,C++ headers 不会将名称放入全局命名空间(C 标准库名称和不能命名空间的宏除外)。但是,只有在没有名称空间范围的情况下可以访问 UDL 时,才能使用 UDL。因此,公开 UDL 的标准习惯用法是坚持,如果您想在某些本地代码中使用文字,正确使用的习惯用法是自己编写 using
声明。你希望这些在具有 using
范围的地方,如函数定义, 而不是 全局或 namespace
范围内。
在使用 C++20 模块的代码库中,处理这些事情要容易得多,因为导入模块只会泄漏 using
指令,前提是您明确选择从该模块导出它。因此,在模块中全局声明这样的指令不一定会破坏包含该模块的任何代码。
在std::literals
命名空间中有一些字面运算符和它们对应的header如operator""s
、operator""sv
等
我想知道为什么这些运算符在包含相应的 header 时不会自动导出,因为它们不会相互冲突或 user-defined 必须以下划线开头的文字运算符,通常像我这样的用户想要在包含 header.
时使用它们如果 using std::string_literals::operator""s;
已经在 <string>
header 以及其他库中,那就太好了:
#include <string> // automatically export the literal operators
#include <chrono> // automatically export the literal operators
int main() {
auto str = "hello world"s;
auto sec = 10s;
}
我看不出有什么坏处。为什么委员会不喜欢这样?它有什么问题或者这是一种不好的做法吗?
在 C++ 中,using
声明 无法 撤消。一旦它在那里,它后面的每一段代码(在它的范围内)都会有它的名称查找规则受该指令的影响。因此,全局 using
语句有些危险。它在 header 中更加危险,因为这将固有地影响包含 header(包括任何 header 的每个文件的行为在 之后 header).
因此,C++ headers 不会将名称放入全局命名空间(C 标准库名称和不能命名空间的宏除外)。但是,只有在没有名称空间范围的情况下可以访问 UDL 时,才能使用 UDL。因此,公开 UDL 的标准习惯用法是坚持,如果您想在某些本地代码中使用文字,正确使用的习惯用法是自己编写 using
声明。你希望这些在具有 using
范围的地方,如函数定义, 而不是 全局或 namespace
范围内。
在使用 C++20 模块的代码库中,处理这些事情要容易得多,因为导入模块只会泄漏 using
指令,前提是您明确选择从该模块导出它。因此,在模块中全局声明这样的指令不一定会破坏包含该模块的任何代码。