例如,在<algorithm>
中,函数equal_range
返回一个pair
,那么我可以假设如果I #include <algorithm>
,<utility>
是#include
d吗?
从来没有保证包含其他头文件所依赖的头文件。幸运的是,通常的做法(尽管不是100%)是保护头文件不被多次包含——这意味着你可以随心所欲地#包含它们,而不会造成伤害。
您应该始终包含您需要的内容,不能依赖于在另一个标头中包含相同标头集的所有实现。
在您的示例中,如果一个函数返回一对,您可以合理地确定pair
类已声明,但不需要实现包含<utility>
的其余部分。
事实上,不可能完全使用标准中显示的头来实现标准库,因为存在一些循环引用。实现必须将它们拆分为更小的部分,并将这些子标头包含在所需的<>
标头中。
例如,GCC团队正在努力减少包含的数量,以加快编译时间。
好的,答案很晚,但我还是会添加这个。
这是关于<iostream>
标头的。在C++98和C++03中,标准没有保证它会包括<istream>
和<ostream>
,这意味着不能保证您有可用的std::endl
。至少有一位编译器坚持要正式对待它(尽管标准中所有的非规范性例子都表明了的意图)!
嗯,我不记得是谁先指出的,但在[comp.lang.c++]中,它被上下左右讨论了好几次。最后,詹姆斯·坎泽,祝福他的灵魂(他还没有死,事实上他在SO上),把它提交给委员会,它被固定为C++0x。
所以,现在有一个可以依赖的头依赖项。
哈利路亚!
但在另一个方向上,C++0x增加了关于哪些标头可以将哪些名称放入全局命名空间和std
命名空间的混乱。现在,任何与C库头相对应的标准库头都可以自由地污染全局名称空间,并且是一致的。因此,现在包含<cstdio>
是没有意义的,但现在明智的做法是包含<stdio.h>
,并接受保证的全局命名空间污染。
干杯&hth。,
是的,您不应该假设任何关于包含头的内容。一段时间以来,我一直在尝试包含头文件,你知道,我观察到,当涉及到像矢量和字符串这样的头文件时,你几乎可以肯定你在某个地方包含了它们。是的,但只有当你只是在玩的时候,这些东西才是好的。我建议你总是包括标题。
没有保证,但由于<algorithm>
在内部使用pair,因此它应该包含它是常识。有一些方法可以确保头文件只包含一次:
#pragma once
http://en.wikipedia.org/wiki/Pragma_once
#ifndef MY_H
#define MY_H
//header code
#endif /* MY_H */
通常,一个好的库会包含所有需要编译的文件,并且这些文件将使用这种机制来确保它们只包含一次。
这个规则有时也有例外,尤其是在私人(个人,而非标准)库中,其中包含的头文件按照编译所需的顺序放置。在这种情况下,如果有三个include,那么第二个include可能使用第一个和第三个的代码。
最好的方法是包含所有您需要直接访问您使用的数据结构的内容。