-1

I have used std::invalid_argument exception class in my code. So I also had included the header <exception> in the precompiled header (pch.h in my case). But then I removed <exception> from pch.h and the code compiled successfully on GCC 11.2 and I was surprised.

Here are some examples:

#include <exception> // removing this does not have any effects
#include <array> // the same here
.
.
.
throw std::invalid_argument( exceptionMsg ); // somewhere in the code
.                                            // how does this work?
.
.
std::array<int, 4> buffer { }; // somewhere in the code
.                              // how does array work without #include <array> ??
.
.

Similarly, I removed <iterator>, <array>, <cstring>, etc. from the pch.h and still no issue. How is this possible?

So if including headers is not going to help when compiling the code, then what is their purpose? Is it safe to remove these #includes if the compiler does not complain?

digito_evo
  • 3,216
  • 2
  • 14
  • 42
  • 2
    The Standard Headers __may__ include other Standard Headers, this is implementation dependent. Always include the necessary headers. Also you may be having rebuild problems try a full clean between test. We like to see a [mcve] so we can checkout any problems for ourselves. How are you using precompiled headers with GCC, the filename `pch.h` is commonly used in MSVC for pre-compiled headers ? – Richard Critten Nov 27 '21 at 18:54
  • 2
    FYI, `std::invalid_argument` is defined in ``, not `` – Remy Lebeau Nov 27 '21 at 19:00
  • If you're confused about headers, the first thing to do is get rid of `pch.h`. It's not really a header, and it can do abominable things. It's never necessary. It's used to speed up compilation in some situations. If you don't know why it's there, get rid of it. – Pete Becker Nov 27 '21 at 20:55
  • @Pete Becker I use it for the same reasons you mentioned. Another guy told me I have to check all the identifiers that I've used in the code and then add the necessary headers based on them and I did that. Hopefully, it won't cause much trouble in the future. – digito_evo Nov 28 '21 at 07:02

1 Answers1

3

But then I removed from pch.h and the code compiled successfully on GCC 11.2 and I was surprised.

This isn't unusual. You'll get used to it.

How is this possible?

This can happen when one of the headers that you still include happens to also include those headers that you don't directly include.

Is it safe to remove these #includes if the compiler does not complain?

No. It's not safe to not directly include a header that you depend on. When one header stops including another header, then that header may end up being not included at all, and if you depend on that header, then your program will stop compiling. To avoid that from happening, always directly include all headers that you depend on.

eerorika
  • 232,697
  • 12
  • 197
  • 326
  • Is there any way to check to see if I have included all the necessary headers? Or is it more complicated than that? – digito_evo Nov 27 '21 at 19:11
  • @digito_evo Read through all identifiers that you use, check documentation for where it is declared / defined, and check whether you've included that or not. The steps are simple, but it's a lot of work unless you can memorise a lot of identifiers. – eerorika Nov 27 '21 at 19:13
  • I see. My other question is, have `modules` in C++20 fixed these issues? – digito_evo Nov 27 '21 at 19:16
  • 1
    @digito_evo Modules should make it possible to avoid the problem. But it won't solve anything until everything that you use has been modularised. And since the standard library isn't modular in C++20, that in particular hasn't been solved. – eerorika Nov 27 '21 at 19:18
  • That is sad. I hope they fully implement it before C++23 comes out. – digito_evo Nov 27 '21 at 19:22