gpt4 book ai didi

c++ - pragma once inside 和 outside 之间的区别包括守卫?

转载 作者:可可西里 更新时间:2023-11-01 15:56:01 24 4
gpt4 key购买 nike

#pragma once 放在 include 守卫内部和外部有什么区别吗?

案例一:

#ifndef SOME_HEADER_H
#define SOME_HEADER_H
#pragma once

案例二:

#pragma once
#ifndef SOME_HEADER_H
#define SOME_HEADER_H

我只是出于好奇想知道是否有任何特殊情况我应该更喜欢一个或另一个(情况 1 或情况 2),因为我决定在我的代码中结合两者(pragma 和 header guards)。

编辑:

我认为你们误解了我的问题...我问的是 pragma once 的位置,而不是 pragma once -vs- header guards。

最佳答案

有一个微妙的区别,如果在包含 header 之前已经定义了 SOME_HEADER_H,那么在第二种情况下,预处理器将处理 #pragma once,而在第一种情况不会。

如果您 #undef SOME_HEADER_H 并通过相同的 TU 再次包含该文件,您将看到功能上的差异:

#define SOME_HEADER_H
#include "some_header.h"
#undef SOME_HEADER_H
#include "some_header.h"

现在,在案例 1 中,我拥有头文件中的所有定义。在情况 2 中我没有。

即使没有 #undef,您也可以想象到,由于 #pragma once 在情况 1 中被忽略,因此预处理时间会有所不同。这取决于实现。

我可以想到在第一次包含这个头文件之前已经定义了两种合理的方式:

  • (明显的)一个完全独立的文件定义它,有意或无意的名称冲突,
  • 这个文件的拷贝已经定义了它。根据可能包括此文件以两个不同文件名参与同一 TU 的情况的实现,例如因为符号链接(symbolic link)或文件系统合并。如果您的实现支持 #pragma once,并且您非常仔细地检查了它的文档,您可能会找到一个明确的声明,是通过包含文件的路径应用优化,还是通过比较标识文件存储的东西,如 inode 号。如果是后者,您甚至可以弄清楚是否仍然存在可以用来欺骗预处理器的骗局,例如远程安装本地文件系统以隐藏它“确实是同一个文件”......

虽然以预期的方式使用,但只要实现以 Microsoft 定义的方式对待 #pragma once 就没有区别。只要它被处理而不是被跳过,它就会标记优化的包含文件,所以它是否会在第二次遍历文件时被处理并不重要——第二次遍历不会发生。

当然,由于编译指示是非标准的,至少在理论上,它在不同的实现中可能具有完全不同的含义,在这种情况下,何时以及处理多少次可能很重要。实际上,您会认为没有人会这样做。

关于c++ - pragma once inside 和 outside 之间的区别包括守卫?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/5382404/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com