可能重复:
what is the difference between #include <filename> and #include “filename”
除了编译器搜索路径的方式之外,两个#include语法之间是否存在根本区别?
我觉得英特尔的编译器没有提供完全相同的输出。
答案 0 :(得分:23)
基本差异是,其中搜索路径。
您应该使用“系统”包含的尖括号形式,以及项目本地包含的常规引号。
答案 1 :(得分:22)
C语言标准说<>
用于“标题”,""
用于“源文件”。现在,不要全神贯注于“源文件”的事情。当标准说“源文件”时,它并不意味着你的想法。标准中使用的术语“源文件”包含我们俗称的“头文件”(除了我们通常称之为“源文件”)。
当标准谈到“标题”时,它根本没有特别谈论文件。该标准不要求标题作为文件存在。它们可以内置于编译器中,用于所有标准维护。
<>
和""
之间的真正的区别在于<>
用于标题和""
用于文件。如果您知道要包含的来源是文件,那么您应该使用""
。
在实践中,编译器对<>
与""
使用不同的搜索算法。标准允许这样做,因为用于任何一个的搜索算法是实现定义。但这并不是标准所表达的真正差异。
答案 2 :(得分:7)
Dan Molding做对了;放松,黑客和尼克巴斯汀弄错了。遗憾。
#include <...>
适用于标题,它甚至不需要是文件系统中的文件,但可以是在编译器内部。
#include "..."
适用于文件,并且只有在找不到此类文件时,它才会默认返回#include <...>
。
查找这些标头和文件的方式和位置,以及是否&lt; &GT;应该用于系统文件,“”用于项目文件,这确实是一个常见的约定,完全取决于编译器和项目。
C标准(ISO / IEC 9899:1999)说(强调我的):
6.10.2源文件包含
约束
#include
指令 应标识标头或源文件 可以由。处理 实施语义
表单
的预处理指令
#include <h-char-sequence> new-line
搜索序列 a的实现定义的位置 标题由唯一标识 &lt;指定序列和&gt; 分隔符,并导致替换 该指令的全部内容 标题的内容。怎么样的地方 指定或标识标题 是实现定义的。
表单
的预处理指令
#include "q-char-sequence" new-line
导致替换它 指令由整个内容组成 由...标识的源文件 指定序列之间的“ 分隔符。命名的源文件是 在&gt;中搜索实现定义的方式。 如果这 搜索不受支持,或者如果 搜索失败,指令是 重新处理就像读了
#include <h-char-sequence> new-line
与相同 包含序列(包括&gt; 来自原文的字符(如果有的话) 指令。
答案 3 :(得分:6)
引用指示首先在当前目录中搜索,然后在系统目录中搜索(在编译器/预处理器中硬编码的路径或用-I
指定的路径)。通过使用尖括号,您可以选择不先搜索当前目录。
编译器输出肯定不依赖于引号,因为它是在预处理阶段处理的。除了由于搜索行为改变而导致包含不同文件的情况。
答案 4 :(得分:3)
对于gcc编译器,&lt;&gt;之间存在 之差和“”标题。如果&lt;&gt;标头包含在作为预处理器的系统提供的目录中,然后不会为包含的标头发出警告。使用 -Werror ,这在某些情况下会产生巨大的差异。
英特尔编译器也有-isystem指令,所以它也可能适用于icc。
更不用说查找目录中的差异太明显了。
答案 5 :(得分:1)
#include <somefile.h>
将检查系统包含路径(包括为项目添加的任何其他路径)。
#include "somefile.h"
将检查应用程序工作文件夹。 (即与源文件中包含#include语句的文件夹相同)。
答案 6 :(得分:0)
警告:这是纯粹的猜测。我没有足够的经验与英特尔编译器知道它是否以这种方式工作,也不知道任何编译器。
如果编译器实现了预编译的头文件,它可能会将这些文件用于包含但不包含另一种形式的文件。如果预编译的标题与实际标题不同步,则会根据包含的标题得到不同的结果。
答案 7 :(得分:-1)
一般没有技术差异,任何人都会告诉你它只是本地风格,可能受到过去编译器的影响 - 许多现代编译器以完全相同的方式实现初始搜索(通常可以通过命令行使用其他常见行为)选项)。该标准将行为留在了实现者的手中,没有特别的理由来支持这两种语法。
根据ISO C99标准的6.10.2部分,&lt;&gt;的搜索路径和“”都是实现定义的。在标准眼中它们之间的唯一区别是使用“”将依赖于&lt;&gt;如果无法解决。 (不要被标准绊倒,似乎区分“标题”和“源文件” - 标准实际上没有区别,除了保留一些名称这一事实 - “stdio.h “等等。)