Forward declaration include, on top of declaration include (ClassFwd.h + Class.h)

半城伤御伤魂 提交于 2019-11-27 21:48:37

问题


In Effective C++ (3rd edition), Scott Meyers, in Item 31, suggests that classes should have, on top of their classic Declaration (.h) and Definition (.cpp) files, a Forward Declaration Include File (fwd.h), which class that do not need the full definition can use, instead of forward declaring themselves.

I somewhat see the case for it, but I really don't see this as a viable option... It seems very hard to maintain, rather overkill and hardly necessary.

I can, however, see its use for template forward declarations, which are rather heavy. But for simple classes? It seems to be that it's a pain to maintain and will create a whole lot of almost empty include files that serve a very small purpose... is it worth the hassle?

Here's a example:

// Class.h
class Class
{
    Class();
    ~Class();
};

// ClassFwd.h
class Class;

// Class.cpp
Class::Class()
{
}

Class::~Class()
{
}

My question:

What do you guys think? If this a good practice?

NOTE I am mostly interested in the arguments FOR this practice, to see if I missed something that would make me agree with Scott Meyers.


回答1:


I used forward declaration header files for all my libraries. A library would typically have this structure:

lib/
  include/
    class headers + Fwd.h
src/
  source files + internal headers

The lib/include directory would contain all public classes headers along with one forward declarations header. This made the library light-weight on the include side. Any header outside of this library only includes the forward header (Fwd.h), while sources outside of this library includes the necessary complete headers. One can also provide a convenience header (Lib.h) that includes all the other headers, for use in source files.

Another thing to place in the forward declaration header is typedefs for shared_ptr, especially in the case of an inheritance hierarchy with factory classes that return pointers to implementations.

The above is useful for larger applications with lots of internal libraries. A refinement of the above for this case would be to place the public headers in lib/include/lib. This way clients of your library would have to include lib/.... Think of this as a namespace for your headers.

Good luck!




回答2:


Placing a simple class Whatever; in its own header has no advantages and lots of disadvantages.

Especially in the case where accessing a header can be time consuming, one uses simple forward declarations to avoid accessing headers; putting them in their own headers would defeat the purpose...

With templated things, as you note, it's a different matter. E.g. check out <iosfwd> from the standard library.

Cheers & hth.




回答3:


The practice allows the code user not to think about whether a class is regular or template. The user just #inludes "corresponding_fwd.h" file and has a class reference. One less annoyance for the user is A Good Thing. But if it's a small project or class' creator is the only class' user then it might be more annoyance. So, it depends.




回答4:


If you have a large solution this is your only chance to handle the inherent dependencies:

struct A {
    B* m_pB;
};

struct B {
    A* m_pA;
};

Now A and B may reasonably be in different header files, maybe even different projects. Yet, their dependency is not some design defect but entirely logical and necessary. What do you do?

  1. First include a single Types.h forward-declarating header for eeach required project, i.e., the forward declaration does not have its own header file per class.
  2. Then include the Class.h of all required projects. These headers will require forward declarations to compile.
  3. Include the headers of the main project.

In a rather large solution (500k LOC) I've found this pattern to be very easily manageable. Otherwise, if you change a class declaration, where do you find all forward declarations that you may have made individually in any number of other header files?



来源:https://stackoverflow.com/questions/3935183/forward-declaration-include-on-top-of-declaration-include-classfwd-h-class-h

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!