简体   繁体   English

在Visual Studio中包括头文件

[英]Including header files in Visual Studio

Suppose I have a solution with 3 projects X , Y , and E . 假设我有3个项目XYE的解决方案。

E will generate an executable and X and Y will generate static libraries such that Y includes the header files of X and E includes the header files of Y . E将生成可执行文件, XY将生成静态库,以使Y包括X的头文件,而E包括Y的头文件。

Now, my question is: why do I have to include the directory of the header files of X in E ? 现在,我的问题是: 为什么我必须在E包括X的头文件目录?

Here's why: 原因如下:

  1. It is possible that some function in project Y takes an argument (or returns a value) which is of a type declared in X . 项目Y中的某些函数可能会采用X声明的类型的参数(或返回值)。
  2. If so, the compiler may have to create these argument (or return value) objects while compiling E . 如果是这样,编译器可能必须在编译E创建这些参数(或返回值)对象。
  3. If that's the case, header files from X are absolutely needed in E . 如果是这样,则E中绝对需要X头文件。

It is sometimes possible to restructure header files for C++ to use forward declarations to avoid the situation that you describe. 有时可以为C ++重组头文件以使用前向声明来避免您描述的情况。 Here is an example: C++ header dependency tricks . 这是一个示例: C ++标头依赖技巧

A simple case: 一个简单的例子:

Xh h

class X {
  //...
};

Yh h

// #include <X.h> -- remove this
class X; // add forward declaration
class Y {
  X *m_px; // must be a pointer, not a value,
           // otherwise the size of X would need to be known
  //...
};

Y.cpp pp

#include <X.h> // need to add it here
//...

You can avoid this situation if you construct Y such that its dependencies on X are completely encapsulated. 如果构造Y以完全封装对X的依赖关系,则可以避免这种情况。 This may or may not be possible depending on the specifics of X and Y. But if the interface the Y presents to E doesn't need to have any details of X in it, then the E project shouldn't need to even indirectly include headers from X. In thins case only the implementation files of Y (the .c or .cpp files) would include headers from X. Using forward declarations for types in X in the Y headers could help achieve this encapsulation of X in Y. 根据X和Y的具体情况,这可能实现或不可能实现。但是,如果Y向E展示的接口不需要在其中包含X的任何细节,那么E项目甚至不需要间接包括在稀疏情况下,仅Y的实现文件(.c或.cpp文件)将包括X的头。在Y头中对X中的类型使用前向声明可以帮助实现X在Y中的封装。

This is a good goal to reach for, but it might not always be possible and even when it is possible it might be more effort than you (or your management) might want to put forth. 这是一个很好的目标,但并非总是可能的,即使有可能比您(或您的管理层)想要付出的努力更多。

Short answer: "Why do I have to include the directory of the header files of X in E?"... You shouldn't. 简短的答案: “为什么我必须在E中包含X的头文件的目录?” ...您不应该这样做。 Client's of Y should not have to know that Y depends on X. Y的客户不必知道Y取决于X。


Long answer: You need to include the header of X in E only if the interface (signatures) of Y makes use of things declared in the header of X. But if the header of Y were "properly constructed", then they would include the headers of X in the Y header itself and you wouldn't have to include the X header in E explicitly (including the Y header would automatically include the X header). 长答案:仅当Y的接口(签名)使用X的标头中声明的内容时,才需要在E中包括X的标头。但是,如果Y的标头是“适当构造的”,则它们将包括X标头包含在Y标头本身中,而您不必在E中明确包含X标头(包括Y标头将自动包含X标头)。

By "Properly constructed" I meant that if the signatures in Y1.h in Y depend on (say) X3.h and X7.h, then Y1.h should include those files (directly of indirectly). “正确构建”的意思是,如果Y中Y1.h中的签名依赖于(例如)X3.h和X7.h,则Y1.h应该包括那些文件(直接或间接)。 This way, any client of Y1.h would not have to know what it's dependencies are and have to include those dependencies separately as a result. 这样,Y1.h的任何客户端都不必知道其依赖项是什么,因此不必分别包含这些依赖项。 As a simple test, a .cpp consisting of the following line should compile without issues: 作为一个简单的测试,由以下几行组成的.cpp应该可以正常编译:

#include "Y1.h"

A good practice is to #include "Y1.h" before including any other file in Y1.cpp. 一个好的做法是在Y1.cpp中包含任何其他文件之前,先#include“ Y1.h”。 If Y1.h is missing dependencies, the compiler will let you know. 如果Y1.h缺少依赖项,则编译器会通知您。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM