1

假设我有一个包含 3 个项目XY和的解决方案E

E将生成一个可执行文件,并将生成X静态Y库,例如Y包含.XEY

现在,我的问题是:为什么我必须包含 in 的头文件的X目录E

4

4 回答 4

4

原因如下:

  1. 项目中的某些函数可能Y需要一个参数(或返回一个值),该参数是在X.
  2. 如果是这样,编译器可能必须在编译时创建这些参数(或返回值)对象E
  3. 如果是这种情况,X则绝对需要E.
于 2009-10-22T16:16:20.433 回答
1

如果你构造 Y 使得它对 X 的依赖被完全封装,你可以避免这种情况。根据 X 和 Y 的具体情况,这可能会也可能不会。但是如果 Y 呈现给 E 的接口不需要包含 X 的任何细节,那么 E 项目甚至不需要间接包含来自 X 的标头。在精简情况下,只有 Y 的实现文件(.c 或 .cpp 文件)将包含来自 X 的标头。在 Y 标头中对 X 中的类型使用前向声明可以帮助实现 X 在 Y 中的这种封装。

这是一个很好的目标,但它可能并不总是可能的,即使有可能,它也可能比你(或你的管理层)想要付出的努力更多。

于 2009-10-22T17:51:21.553 回答
1

有时可以为 C++ 重构头文件以使用前向声明来避免您描述的情况。这是一个示例:C++ 头文件依赖技巧

一个简单的案例:

Xh

class X {
  //...
};

// #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

#include <X.h> // need to add it here
//...
于 2009-10-22T16:26:11.787 回答
0

简短的回答: “为什么我必须在 E 中包含 X 的头文件的目录?”......你不应该。Y 的客户不必知道 Y 依赖于 X。


长答案:只有当 Y 的接口(签名)使用 X 的标头中声明的东西时,您才需要在 E 中包含 X 的标头。但是如果 Y 的标头是“正确构造的”,那么它们将包括Y 标头本身中的 X 标头,您不必在 E 中显式包含 X 标头(包括 Y 标头将自动包含 X 标头)。

通过“正确构造”,我的意思是如果 Y1.h 中的签名依赖于(比如)X3.h 和 X7.h,那么 Y1.h 应该包括这些文件(直接或间接)。这样,Y1.h 的任何客户端都不必知道它的依赖项是什么,因此必须单独包含这些依赖项。作为一个简单的测试,包含以下行的 .cpp 应该可以毫无问题地编译:

#include "Y1.h"

一个好的做法是在 Y1.cpp 中包含任何其他文件之前 #include "Y1.h"。如果 Y1.h 缺少依赖项,编译器会通知您。

于 2009-10-22T16:27:49.673 回答