传统上,避免C中多个头部包含的标准和可移植方法是使用 #ifndef - #define - #endif
预编译器指令方案,也称为macro-guard scheme(参见下面的代码片段) .
#ifndef MY_HEADER_HPP
#define MY_HEADER_HPP
...
#endif
然而,在大多数实现/编译器中(见下图),有一个更多的"elegant"替代方案与宏监护方案#pragma once具有相同的用途 . 与宏保护方案相比, #pragma once
具有几个优点,包括更少的代码,避免名称冲突,有时提高编译速度 .
做了一些研究,我意识到虽然几乎所有已知的编译器都支持 #pragma once
指令,但是对于 #pragma once
指令是否属于C 11标准仍然存在紊乱 .
问题:
-
有人可以澄清
#pragma once
指令是否属于C 11标准? -
如果它不是C 11标准的一部分,是否有计划将其包含在以后的版本中(例如,C 14或更高版本)?
-
如果有人可以进一步详细说明使用其中一种技术(即,宏保护与
#pragma once
)的优点/缺点,也会很好 .
2 回答
#pragma once
不标准 . 它是一种广泛的(但不是通用的)扩展,可以使用如果您的可移植性问题有限,并且
您可以确保所有包含文件始终位于本地磁盘上 .
它被认为是标准化,但被拒绝,因为它无法可靠地实施 . (当您通过多个不同的远程安装程序访问文件时会出现问题 . )
确保在单个开发中不存在包含保护冲突是相当容易的 . 对于可能被许多不同开发项目使用的库,显而易见的解决方案是在创建包含防护时生成大量随机字符 . (无论何时打开新 Headers ,都可以设置一个好的编辑器来执行此操作 . )但即使没有这个,我还没有遇到任何库之间冲突的问题 .
标准的第16.6节(N3936草案)将
#pragma
指令描述为:基本上
#pragma once
是#pragma
指令的实现特定实例,不,它不是标准的 . 然而 .它通常得到大多数人的支持,包括GCC和Clang,因此有时建议避免使用包含防范的样板 .