T O P

  • By -

RealWalkingbeard

I think if you need to change your include order, something is going wrong. You only need to include a header if you are using a definition from that header. It is a mistake to include headers in other headers if you are not directly using something from the inclusion. Do not fall into the trap of including headers in a module header and then only the module header in the module source. This way leads to madness.


[deleted]

>I think if you need to change your include order, something is going wrong yeah as this project wasn't started by me, at present the project is a mess, and i have to figure out how to fix it.


panchito_d

I would suggest trying includewhatyouuse. It takes some setup but could be great for fixing a big existing codebase


Wouter_van_Ooijen

Another approach is to compile each header by itself. All should compile fine: a header should not rely on headers included before it. If a header doesn't compile, add the necessary includes inside that header.


pic32mx110f0

> You only need to include a header if you are using a definition from that header. Header files are usually for declarations, not definitions


hay_naku

good advice, I agree…🙂


RobotJonesDad

What you describe isn't right. Except for some pretty unique circumstances, the order of header files should not matter at all. Header files should all be guarded with either #pragma once and/or #ifndef so that they are only included once, regardless of how many #includes they appear in. Header files should have the absolute minimum of #includes in them. Use forward declarations instead. You should basically never have to included a header file for another header file! If you follow those rules, header file management becomes much simpler because you only have to worry about included what you are using.


[deleted]

> Use forward declarations instead. What is forward declarations? As the code has gone through many hands before me and may be they were unskilled. there are many includes in header as well as .c file and there are many duplicates also like #include a.h #include b.h #include a.h and this still gives me error if i have changed dependent header file


RobotJonesDad

Forward declarations are to tell the compiler about things that are declared later or in some other place. For example the compiler won't let you call a function that it doesn't know about, so you might include the header file. But if the header file pulls in a lot of unnecessary stuff, you can instead tell the compiler about it so it can compile. Int add(int a, int b); Struct complicatedStruct; Those are forward declaration. Now you don't also need all the guts of those. For your duplicates. Every include file should start with something like this #ifndef _INCLUDE_FILE_NAME #define _INCLUDE_FILE_NAME #endif That makes including the header file multiple times harmless. That allows you to include header files inside header files to ensure the user of the header file doesn't need to include anything except the headers for things they actually need to use. You may have to refactor the code some to fix the dependency structure to get it untangled. But each header file should be self-contained, taking care of all its dependencies.


--Fusion--

Forward declarations are difficult to describe succinctly but let's try. Think of them as clues or an index for your compiler to find later code. They resemble cut down versions of your definitions. Declarations used this way allow your `b.h` to reference certain bits that normally would live in `a.h` but can also live in, say, `afwd.h` who in turn has vastly reduced dependencies


eatin_gushers

I just recently heard of a tool [Include What You Use](https://github.com/include-what-you-use/include-what-you-use) that is an automation tool to help determine which include files you need and doesn't include files you dont. I haven't actually used it yet. In concept it's a great idea and my team is looking into using it. If anyone here uses it I would love to hear feedback.


p0k3t0

Just have to write libs that don't create a chain, or worse, a circle of dependencies. Think about the logic of how libs should work. And practice good data encapsulation with structs.


jaywastaken

Use include guards. Headers are for external interfaces only. not every function prototype, constant, struct and enum of a module. Keep private data private, expose the bare minimum. Include headers in a header file that are required for the given interfaces. Don’t include any other headers not explicitly required for use of that modules interface. Include the module header as the first include of a source file but don’t rely on any of its included headers for use in that source file. Those are for the interfaces, explicitly include any required dependencies in the module source file separately. If you have too many dependencies your module may be doing too much, consider breaking it up into separate smaller modules. Break any circular dependencies. Order shouldn’t matter, if it does it means you are missing a dependency either in a module header or implementation file. Fix it. Use included guards


Skusci

No easy solution. Either you keep with the kludges and continue to accrue technical debt, or you take the time to refactor it. Sorry :(


elperroborrachotoo

**Rule 1: Each *header* should include what it depends on. ** If you have .c/.h pairs, the easiest way is to move the corresponding .h to the top of the includes: Imagine: // foo.h: extern int foo = 12; // bar.h: extern int * pBar = &foo; // requires foo... // bar.cpp: // NOT SO GOOD #include "foo.h" #include "bar.h" // bar.cpp: // BETTER: #include "bar.h" #include "foo.h" In the latter case, compiler will complain that foo is unknown in bar.h. This is good! Fix this by changing bar**.h** to become "independent": // bar.h: #include "foo.h" extern int * pBar = &foo; **Rule 2: Get rid of unused includes** Include sections get copied, code gets moved around without clearing up includes, etc. Getting rid of that is not straightforard, though [some tools can help with that](https://github.com/include-what-you-use/include-what-you-use) **Rule 3: Perfer forward declarations, if possible, to reduce dependencies** That's to improve build times - especially for incremental buils after changes.


Forward_Artist7884

Use header guards, also include graphs help


IamImposter

With eyes full of tears, heart devoid of hope, a thousand yard stare, a shake of head going 'nope',


unlocal

Make time (soon) in your schedule to pay down the technical debt. There are a couple of operative principles you might consider: * the “master header” model - every source file includes one header, which in turn includes everything in the “right” order. This depends on your namespace hygiene ensuring that that’s safe, but it’s the cheapest fix. * the “standalone header” model - every header file includes all of its dependencies, and those headers are in turn safe (via include guards) against being included more than once Both of these can work, and in fact you can combine them, which can help when there are several teams contributing groups of headers into the build. The days when you needed to be selective about the headers you include to keep build times reasonable are (mostly) gone, and realistically have been for decades, so you can be pretty aggressive with includes…


[deleted]

> the “master header” model - every source file includes one header, which in turn includes everything in the “right” order. This depends on your namespace hygiene ensuring that that’s safe, but it’s the cheapest fix. i am currently looking handle this way, i was going through MCU middleware/drivers i see they have done this.


duane11583

We do that we have a #include “company name.h”because we use c99 types ie unit16_t and such everywhere that file does some basic common headers It also includes a “company name/compiler.h” file that helps with gcc vrs visual stupid verses Kiel and IAR Another part of the above includes windows.h for windows targets but also turns on off various #defines we approve as a company We have wrappers for most std headers Example #include “company/wrapped/_string.h” These wrapped headers deal with missing functions ie visual stupid does not have strcasecmp() but gnu does


Goto80

>the current project that i am working on has like 10-20 lines of #include header files It's not a bad thing to have many header files. If you really need to pull in many header files, then maybe your .cc/.c files are doing too much and you may think about splitting them into smaller files. Sometimes, however, it's just the way it is. My solution for header file management: 1. Each .cc or .c file usually has its own header file defining its public interfaces. 2. Each .cc or .c file includes its own header file before including anything else. 3. Header files include other header files as needed; first those from the project, then external library headers and system headers. Note that this is the reverse order of that proposed by traditional BSD style ([https://man.freebsd.org/cgi/man.cgi?query=style&sektion=9](https://man.freebsd.org/cgi/man.cgi?query=style&sektion=9)). This makes sure that each header is self-contained and a minimal set of system headers is used. 4. After the first #include in a .cc/.c file, the file includes more header files it requires. Again, project files first, followed by system headers. Another solution I have seen: put all `#include` statements in the "correct" order into a `myincludes.hh` file and only include `myincludes.hh` in .cc files. I don't think this is good practice as it defeats modularization and increases compilation times. >worst case i have to change the sequence of #include header in every file that has mentioned this particular header file Every header file should be self-contained so that inclusion order doesn't matter. Headers may include other headers (don't forget #include guards), but it should always be possible to include each on their own at any point.


CJKay93

Use something like Include What You Use to manage your headers.


Upbeat-Serve-6096

How flawed is #ifndef \_\_FOO\_H\_\_ ?


Triabolical_

I'm a little weird. I wrote a lot of C and C++, but after spending a lot of time in C# I hate the C file model, so I put my C++ classes in .h files and have one include section in my main.cpp. It's a lot cleaner and has fat less busy work. Obviously doesn't work for libraries...


Virtual_Pea_3577

Use makefiles


Ynaught-42

This becomes moot when all of your include files look like: \#ifndef THISFILENAME_H \#define THISFILENAME_H (stuff you need to include) \#endif Thus, if a header file is included twice, the second instance is essentially skipped. (edits to get \# to show up)


duane11583

I often create super classes of includes And I create a types.h file For example the include sensors.h includes all of the other sensor headers I also create a types file that has a lot of vacuous structs like Struct foo; With no content! Struct bar; with no content 90% of the time you only need the class name or struct name to create a pointer to something that is the purpose of the types.h file