【发布时间】:2010-10-01 07:00:05
【问题描述】:
我在玩 gmock 并注意到它包含这一行:
#include <tuple>
我会期待tuple.h。
什么时候可以排除扩展,它是否赋予指令不同的含义?
【问题讨论】:
标签: c++ include c-preprocessor standards
我在玩 gmock 并注意到它包含这一行:
#include <tuple>
我会期待tuple.h。
什么时候可以排除扩展,它是否赋予指令不同的含义?
【问题讨论】:
标签: c++ include c-preprocessor standards
C++ 标准头文件没有“.h”后缀。我相信原因是该标准会破坏许多不同的标准前实现。因此,标准委员会没有要求供应商将其现有的“iostream.h”(例如)标头更改为符合标准(这将破坏其现有用户的代码),而是决定他们将删除后缀(我相信不会那么现有的实施已经完成)。
这样,现有的非标准程序将继续使用供应商的非标准库工作。当用户想让他们的程序符合标准时,他们将采取的步骤之一是更改“#include”指令以删除“.h”后缀。
所以
#include <iostream> // include the standard library version
#include <iostream.h> // include a vendor specific version (which by
// now might well be the same)
正如其他答案所提到的,非标准库的编写者可以选择任一命名约定,但我认为他们希望继续使用“.h”或“.hpp”(正如 Boost 所做的那样)。原因:
请注意,当委员会向 STL 添加哈希映射时,也发生了类似的问题 - 他们发现已经存在许多(不同的)hash_map 实现,因此没有提出一个破坏今天有很多东西,他们称标准实现为“unordered_map”。命名空间本应有助于防止这种类型的跳跃,但它似乎不够好(或使用得不够好),无法让他们在不破坏大量代码的情况下使用更自然的名称。
请注意,对于“C”标头,C++ 允许您包含 <cxxxxxx> 或 <xxxxxx.h> 变体。以“c”开头且没有“.h”后缀的声明将其声明放在std 命名空间(可能还有全局命名空间)中,带有“.h”后缀的声明将名称放置在全局命名空间中(一些编译器还将名称放在 std 命名空间中 - 我不清楚这是否符合标准,尽管我没有看到危害)。
【讨论】:
using namespace std; 挥之不去,不幸的是 (因为在 C++ 中,向后兼容才是王道)委员会认为这需要使用不同的名称。
伙计们,
我认为交易是:#include
请注意我可能是错的...这就是我认为它的工作方式(在 Solaris 上的 Forte cc 中)。
【讨论】:
除了已经发布的很好的答案之外,应该注意的是,C++ 标准不需要指令“#include <iostream>”来读取名为“iostream”甚至“iostream.h”的文件。它可以被命名为“fuzzball”。或者,可能不存在相应的文件,并且定义被构建到编译器中并由 include 指令激活。
【讨论】:
没有什么特别的事情发生。该文件被简单命名为tuple。
原因...标准库头文件没有文件扩展名是因为namespaces。
命名空间是在游戏后期与 C++98 标准一起添加到 C++ 标准的,包括所有标准库实体所在的 std 命名空间。
当标准库被移动到 std 命名空间时,这意味着所有现有的 C++ 代码都会中断,因为所有代码都希望该库位于全局命名空间中。解决方案是不理会旧的“dot-h”头文件,并在没有扩展名的文件中提供命名空间库。
这样,#include<iosteam.h> 的旧代码可以期待一个全局的cout,而新代码可以#include<iostream> 并期待一个std::cout。
【讨论】:
我的理解是#include 元组将“指向” tuple.h。
【讨论】:
它包含一个简单命名为“元组”的文件——文件本身没有扩展名。
C++ 包含文件的假定标准是在命名它们时不带 .h 扩展名;许多库编写者遵循此标准(STL 等),但有些不遵循。
【讨论】:
如果文件名为tuple,则需要#include <tuple>
如果它被命名为tuple.h,那么你需要#include <tuple.h>
就这么简单。您没有省略任何扩展名。
【讨论】: