I heard some people complaining about including the windows header file in a C++ application and using it. They mentioned that it is inefficient. Is this just some urban legend or are there really some real hard facts behind it? In other words, if you believe it is efficient or inefficient please explain how this can be with facts.
I am no C++ Windows programmer guru. It would really be appreciated to have detailed explanations.
*Edit: I want to know at compile time and execution. Sorry for not mentioning it.
windows.h is not a "code library". It's a header file, and doesn't contain any executable code as such (save for macro definitions, but those still aren't compiled - their expansions are, if and when you use them).
As such, looking at it strictly from performance perspective, merely including it has any effect solely on compilation time. That one is rather significant, though - for example, if using Platform SDK headers that come with VS2010, #include <windows.h> expands to ~2.4Mb of code - and all that code has to be parsed and processed by the compiler.
Then again, if you use precompiled headers (and you probably should in this scenario), it wouldn't affect you.
If you precompile it, then the compilation speed difference is barely noticeable. The downside to precompiling, is that you can only have one pre-compiled header per project, so people tend to make a single "precompiled.h" (or "stdafx.h") and include windows.h, boost, stl and everything else they need in there. Of course, that means you end up including windows.h stuff in every .cpp file, not just the ones that need it. That can be a problem in cross-platform applications, but you can get around that by doing all your win32-specific stuff in a static library (that has windows.h pre-compiled) and linking to that in your main executable.
At runtime, the stuff in windows.h is about as bare-metal as you can get in Windows. So there's really no "inefficiencies" in that respect.
I would say that most people doing serious Windows GUI stuff would be using a 3rd-party library (Qt, wxWidgets, MFC, etc) which is typically layered on top of the Win32 stuff defined in windows.h (for the most part), so as I said, on Windows, the stuff in windows.h is basically the bare metal.
There are multiple places where efficiency comes in to play.
Including <windows.h> will substantially increase compile times and bring in many symbols and macros. Some of these symbols or macros may conflict with your code. So from this perspective, if you don't need <windows.h> it would be inefficient at compile time to bring it in.
The increased compile time can be mitigated somewhat by using precompiled headers, but this also brings with it a little more codebase complexity (you need at least 2 more files for the PCH), and some headaches unique to PCHs. Nonetheless, for large Windows project, I usually use a PCH. For toy or utility projects, I typically don't because it's more trouble than it's worth.
Efficiency also comes in to play at runtime. As far as I know, if you #include <windows.h> but don't use any of those facilities, it will have no effect on the runtime behavior of your program at least as far as calling extra code and that kind of thing. There may be other runtime effects however that I'm not aware of.
As far as the big White Elephant question, "Is Windows Efficient?" I'll not go in to that here other than to say this: Using Windows is much like anything else in that how efficient or inefficient it is depends mostly on you and how well you know how to use it. You'll get as many different opinions on this as people you ask however, ranging from "Winblowz sucks" to "I love Windows, it's awesome." Ignore them all. Learn to code in Windows if you need & want to and then make up your own mind.
As has been noted, #including windows.h slows down compile time. You can use precompiled headers or do a good job of isolating the windows calls only to modules that need them to help with that.
Also, you can add these preproc definitions before the windows.h include like so:
#define WIN32_LEAN_AND_MEAN
#define VC_EXTRALEAN
#include <windows.h>
It will reduce the number of definitions from windows.h and sub-included header files. You may find later on that you need to remove the lean-and-mean, but try it first and wait until the compiler complains about a missing def.
The namespace conflicts are a legitimate gripe, but technically have nothing to do with efficiency, unless you count efficiency of your personal use of time. Considering how many thousands of definitions will be thrown into your namespace, conflicts are bound to occur at some point, and that can be severely irritating. Just use the practice of isolating your Windows calls into modules, and you will be fine. For this, put #include windows.h in the .cpp file, and not the .h file.
I see no basis for thinking that the runtime performance of the executable will be impacted by including windows.h. You are only adding a large number of definitions to the context used by the compiler. You aren't even putting all the definitions into your compiled code--just allocations, function calls, and referencing based on any definitions used in your source code (.cpp).
Another argument could be made that the Windows API types and functions are inherently wasteful of resources or perform inefficiently. I.e. if you want to create a file, there is some monstrous structure to pass to the Windows API. Still, I think most of this is penny-wise/pound-foolish thinking. Evaluate Windows API performance problems case-by-case and make replacements for inefficient code where possible and valuable.
In general, including windows.h is a necessity: if you need windows functions, you have to include it. I think what you're refering to is (among other things) nested inclusion of windows.h. That is, you include a .h that includes itself windows.h, and you also include windows.h in your .cpp file. This leads to inefficiencies, of course, so you have to study very well in your code what .h files are included in each .h file, and avoid including, say, windows.h n times indirectly.
Just including the header without using it will not have any effects in runtime efficiency
It would affect compilation time ..
Related
I have seen a couple of questions on how to detect unnecessary #include files in a C++ project. This question has often intrigued me, but I have never found a satisfactory answer.
If there are some header files included which, are not being used in a c++ project, is that an overhead? I understand that it means that before compilation the contents of all the header files would be copied into the included source files and that would result in a lot of unnecessary compilation.
How far does this kind of overhead spread to the compiled object files and binaries?
Aren't compilers able to do some optimizations to make sure that this
kind of overhead is not transferred to the resulting object files and
binaries ?
Considering the fact, that I probably know nothing about compiler optimization, I still want to ask this, in case there is an answer.
As a programmer who uses a wide variety of c++ libraries for his work,
what kind of programming practices should I follow to keep avoiding
such overheads ? Is making myself intimately familiar with each
library's working the only way out ?
It does not affect the performance of the binary or even the contents of the binary file, for almost all headers. Declarations generate no code at all, inline/static/anonymous-namespace definitions are optimized away if they aren't used, and no header should include externally visible definitions (that breaks if the header is included by more than one translation unit).
As #T.C. points out, the exception are internally visible static objects with nontrivial constructors. iostream does this, for example. The program must behave as if the constructor is called, and the compiler usually doesn't have enough information to optimize the constructor away.
It does, however, affect how long compilation takes and how many files will be recompiled when a header is changed. For large projects, this is enough incentive to care about unnecessary includes.
Besides the obviously longer compile times, there might be other issues. The most important one IMHO is dependencies to external libraries. You don't want your program to depend on more libraries then necessary.
You also then need to install those libraries in every system you want to the program to build on. This can become a nightmare, especially when the next programmer needs to install some database client library although the program never uses a database.
Also, especially library headers often tend to define macros. Sometimes those macros have very generic names which will break you code or which are incompatible with other library headers you might actually need.
Of course any #include is an overhead. The compiler needs to parse that file.
So avoid them. Use forward declarations where ever possible.
It will speed up compilation. See Scott Myers book on the subject
The simple answer is YES its an overhead as far as the compilation is concerned but for runtime it is merely going to create any difference. Reason being lets say you add #include <iostream> (just for example) and assume that you are not using any of its function then g++ 4.5.2 has some additional 18,560 lines of code to process(compilation). But as far as the runtime overhead is concerned I hardly think that it creates a performance issue.
You can also refer Are unused includes harmful in C/C++? where I really liked this point made by David Young
Any singletons declared as external in a header and defined in a
source file will be included in your program. This obviously increases
memory usage and possibly contributes to a performance overhead by
causing one to access their page file more often (not much of a
problem now, as singletons are usually small-to-medium in size and
because most people I know have 6+ GB of RAM).
How do I find which parts of code are taking a long time to compile?
I am already using precompiled headers for all of my headers, and they definitely improve the compilation speed. Nevertheless, whenever I make a change to my C++ source file, compiling it takes a long time (this is CPU/memory-bound, not I/O-bound -- it's all cached). Furthermore, this is not related to the linking portion, just the compilation portion.
I've tried turning on /showIncludes, but of course, since I'm using precompiled headers, nothing is getting included after stdafx.h. So I know it's only the source code that takes a while to compile, but I don't know what part of it.
I've also tried doing a minimal build, but it doesn't help. Neither does /MP, because it's a single source file anyway.
I could try dissecting the source code and figuring out which part is a bottleneck by adding/removing it, but that's a pain and doesn't scale. Furthermore, it's hard to remove something and still let the code compile -- error messages, if any, come back almost immediately.
Is there a better way to figure out what's slowing down the compilation?
Or, if there isn't a way: are there any language constructs (e.g. templates?) that take a lot longer to compile?
What I have in my C++ source code:
Three (relatively large) ATL dialog classes (including the definitions/logic).
They could very well be the cause, but they are the core part of the program anyway, so obviously they need to be recompiled whenever I change them.
Random one-line (or similarly small) utility functions, e.g. a byte-array-to-hex converter
References to (inline) classes found inside my header files. (One of the header files is gigantic, but it uses templates only minimally, and of course it's precompiled. The other one is the TR1 regex -- it's huge, but it's barely used.)
Note:
I'm looking for techniques that I can apply more generally in figuring out the cause of these issues, not specific recommendations for my very particular situation. Hopefully that would be more useful to other people as well.
Two general ways to improve the compilation time :
instead of including headers in headers, use forward declare (include headers only in the source files)
minimize templated code (if you can avoid using templates)
Only these two rules will greatly improve your build time.
You can find more tricks in "Large-Scale C++ Software Design" by Lakos.
For visual studio (I am not sure if it is too old), take a look into this : How should I detect unnecessary #include files in a large C++ project?
Template code generally takes longer to compile.
You could investigate using "compiler firewalls", which reduce the frequency of a .cpp file having to build (they can reduce time to read included files as well because of the forward declarations).
You can also shift time spent doing code generation from the compiler to the linker by using Link-Time Code Generation and/or Whole Program Optimization, though generally you lose time in the long run.
I'm developing a C++ library. It got me thinking of the ways Java and C# handle including different components of the libraries. For example, Java uses "import" to allow use of classes from other packages, while C# simply uses "using" to import entire modules.
My questions is, would it be a good idea to #include everything in the library in one massive include and then just use the using directive to import specific classes and modules? Or would this just be down right crazy?
EDIT:
Good responses so far, here are a few mitigating factors which I feel add to this idea:
1) Internal #includes are kept as normal (short and to the point)
2) The file which includes everything is optionally supplied with the library to those who wish to use it3) You could optionally make the big include file part of the pre-compiled header
You're confusing the purpose of #include statements in C++. They do not behave like import statements in Java or using statements in C#. #include does what it says; namely, loads and parses the entire indicated file as part of the current translation unit. The reason for the separate includes is to not have to spend compilation time parsing the entire standard library in every file. In contrast, the statements you're trying to make #include behave like are merely for programmer organization purposes.
#include is for management of the compilation process; not for separating uses. (In fact, you cannot use seperate headers to enforce seperate uses because to do so would violate the one definition rule)
tl;dr -> No, you shouldn't do that. #include as little as possible. When your project becomes large, you'll thank yourself when you're not waiting many hours to compile your project.
I would personally recommend only including the headers when you need them to explicitly show which functionalities your file requires. At the same time, doing so will prevent you from gaining access to functionalities you might no necessarily want, e.g functions unrelated to the goal of the file. Sure, this is no big deal, but I think that it's easier to maintain and change code when you don't have access to unnecessary functions/classes; it just makes it more straightforward.
I might be downvoted for this, but I think you bring up an interesting idea. It would probably slow down compilation a bit, but I think the concept is neat.
As long as you used using sparingly — only for the namespaces you need — other developers would be able to get an idea of what classes were used in a file by glancing at the top. It wouldn't be as granular as seeing a list of #included files, but is seeing a list of included header files really very useful? I don't think so.
Just make sure that all of the header files all use inclusion guards, of course. :)
As said by #Billy ONeal, the main thing is that #include is a preprocessor directive that causes a "^C, ^V" (copy-paste) of code that leads to a compile time increase.
The best considered policy in C++ is to forward declare all possible classes in ".h" files and just include them in the ".cpp" file. It isolates dependencies, as a C/C++ project will be cascadingly rebuilt if a dependent include file is changed.
Of course M$ compilers and its precompiled headers tend to do the opposite, enclosing to what you suggest. But anyone that tried to port code across those compilers is well aware of how smelly it can go.
Some libraries like Qt make extensive use of forward declarations. Take a look on it to see if you like its taste.
I think it will be confusing. When you write C++ you should avoid making it look like Java or C# (or C :-). I for one would really wonder why you did that.
Supplying an include-all file isn't really that helpful either, as a user could easily create one herself, with the parts of the library actually used. Could then be added to a precompiled header, if one is used.
Suppose i have the following code (literally) in a C++ source file:
// #include <iostream> // superfluous, commented-out
using std::cout;
using std::endl;
int main()
{
cout << "Hello World" << endl;
return 0;
}
I can compile this code even though #include <iostream> is commented-out:
g++ -include my_cpp_std_lib_hack source.cpp
Where my_cpp_std_lib_hack is a file in some central location that includes all the files of the C++ Standard Library:
#include <ciso646>
#include <climits>
#include <clocale>
...
#include <valarray>
#include <vector>
Of course, i can use proper compilation options for all compilers i care about (that being MS Visual Studio and maybe a few others), and i also use precompiled headers.
Using such a hack gives me the following advantages:
Fast compilation (because all of the Standard Library is precompiled)
No need to add #includes when all i want is adding some debugging output
No need to remember or look up all the time where the heck std::max is declared
A feeling that the STL is magically built-in to the language
So i wonder: am i doing something very wrong here?
Will this hack break down when writing large projects?
Maybe everyone else already uses this, and no one told me?
So i wonder: am i doing something very wrong here?
Yes. Sure, your headers are precompiled, but the compiler still has to do things like name lookups on the entire included mass of stuff which slows down compilation.
Will this hack break down when writing large projects?
Yes, that's pretty much the problem. Plus, if anyone else looks at that code, they're going to be wondering where std::cout (well, assume that's a user defined type) came from. Without the #includes they're going to have no idea whatsoever.
Not to mention, now you have to link against a ton of standard library features that you may have (probably could have) avoided linking against in the first place.
If you want to use precompilation that's fine, but someone should be able to build each and every implementation file even when precompilation is disabled.
The only thing "wrong" is that you are relying upon a compiler-specific command-line flag to make the files compilable. You'd need to do something different if not using GCC. Most compilers probably do provide an equivalent feature, but it is best to write portable source code rather than to unnecessarily rely on features of your specific build environment.
Other programmers shouldn't have to puzzle over your Makefiles (or Ant files, or Eclipse workspaces, or whatever) to figure out how things are working.
This may also cause problems for users of IDE's. If the IDE doesn't know what files are being included, it may not be able to provide automatic completion, source browsing, refactoring, and other such features.
(FWIW, I do think it is a good idea to have one header file that includes all of the Standard Library headers that you are using in your project. It makes precompilation easier, makes it easier to port to a non-standard environment, and also helps deal with those issues that sometimes arise when headers are included in different orders in different source files. But that header file should be explicitly included by each source file; there should be no magic.)
Forget the compilation speed-up - a precompiled header with templates isn't really "precompiled" except for the name and the parse, as far as I've heard. I won't believe in the compilation speed up until I see it in the benchmarks. :)
As for the usefulness:
I prefer to have an IDE which handles my includes for me (this is still bad for C++, but Eclipse already adds known includes with ctrl+shift+n with... well, acceptable reliability :)).
Doing 'clandestine' includes like this would also make testing more difficult. You want to compile a smallest-possible subset of code when testing a particular component. Figuring out what that subset is would be difficult if the headers/sources aren't being honest about their dependencies, so you'd probably just drag your my_cpp_std_lib_hack into every unit test. This would increase compilation time for your test suites a lot. Established code bases often have more than three times as much test code as regular code, so this is likely to become an issue as your code base grows.
From the GCC manual:
-include file
Process file as if #include "file" appeared as the first line of the
primary source file. However, the
first directory searched for file is
the preprocessor's working directory
instead of the directory containing
the main source file. If not found
there, it is searched for in the
remainder of the #include "..." search
chain as normal.
So what you're doing is essentially equivalent to starting each file with the line
#include "my_cpp_std_lib_hack"
which is what Visual Studio does when it gathers up commonly-included files in stdafx.h. There are some benefits to that, as outlined by others, but your approach hides this include in the build process, so that nobody who looked directly at one of your source files would know of this hidden magic. Making your code opaque in this way does not seem like a good style to me, so if you're keen on all the precompiled header benefits I suggest you explicitly include your hack file.
You are doing something very wrong. You are effectively including lots of headers that may not be needed. In general, this is a very bad idea, because you are creating unnecessary dependencies, and a change in any header would require recompilation of everything. Even if you are avoiding this by using precompiled headers, you are still linking to lots of object that you may not need, making your executable much larger than it needs to be.
There is really nothing wrong with the standard way of using headers. You should include everything you are using, and no more (forward declarations are your friends). This makes code easier to follow, and helps you keep dependencies under control.
We try not to include the unused or even the rarely used stuff for example in VC++ there is
#define WIN32_LEAN_AND_MEAN //exclude rarely used stuff
and what we hate in MFC is that if u want to make a simple application u will produce large executable file with the whole library (if statically linked), so it's not a good idea what if u only want to use the cout while the other no??
another thing i don't like to pass arguments via command line coz i may leave the project for a while, and forget what are the arguments... e.g. i prefer using
#pragma (comment, "xxx.lib")
than using it in command line, it reminds me at least with what file i want
That's is my own opinion make your code stable and easy to compile in order to to rot as code rotting is a very nasty thing !!!!!
Boost rocks, it is great and extremely powerful, but I hate it everytime I build solution in my Visual Studio 7.1.
It seems Boost has impact on build time (not positive). I cannot remove all Boost usage from my project to compare build times but I tried it on small projects and the difference is meaningful.
I guess the problem is that Boost consists of thousands of header files which include themselves very extensively. So, when I include, say, boost/function.hpp into my header file, it may lead to including hundred of Boost headers.
Is there someone who experienced the same? Any ideas how to solve it?
Rough thoughts:
Add boost to precompiled headers? At least they will be parsed and kept in one file
Do explicit instantination for some Boost templates?
Prepare Boost headers somehow?
Do not include Boost to header files (sounds unreal)
...
PS. Yep, Boost also uses hardcore templating that pretty hard to compiler I guess, so thousands of header files are not the only problem.
I like also boost a lot
Use the precompiled header like you told (that brings most)
When using linked libraries check if you really need them (linking is also quite slow)
Another maybe stupid hint, but was the main source of performance loss on my computer:
check if your antivirus makes an on-access-scan and disable it for the header & source directories (boost and your projects)
Naturally, including boost leads to longer compilations times - just like including any library does. Being (mostly) a template library offcourse leads to quite big performance penalty as all of the logic is implemented in the headers.
I've had good results including (a subset of) boost in precompiled headers. However, I belive that the gain is greatest with MSVC 9. On MSVC 7 I have seen several reports saying that precompiled headers of templates frequently leads to performance penalty. Another crucial aspect determining if you'll see performance gain is to include the appropiate headers in the precompiled header. Only include headers you frequently use, and make sure they are never changed (that is, think three times before including your own headers here)
I do not know if explicit instantination has any effect, even though I doubt it. If anyone has seen any results on this (regardless compiler), it would be very interesting.
"Preparing" boost headers sounds like altering them which sounds like a very bad idea to me. You don't want to end up maintaining customized headers...
May not be so unreal as you might think. Always use as many forward declarations as possible to reduce the "footprint" of each header file. Consider using the Pimpl pattern to avoid including boost headers that are not reflected in the public interface of your class (offtopic: I consider Pimpl to often be unnecessary. Instead I try to slice the classes into smaller pieces, acheiving the same result in a "cleaner" fashion). Don't be afraid to include general, common classes (e.g. shared_ptr) as long as you're consistent in the usage of these classes (if your using them in all your classes you wont see much gain in hiding them away from one header).
Upgrading MSVC (to support parallel builds) will help. However, this is always an issue in C++. To minimize the problem, you need to be very strict and follow guidelines to reduce the footprint of your headers. Now and then you should look through the include-clauses and make sure there are nothing unnecessary included. If you're list of includes done in the header is getting long you're probably doing something wrong - most includes should only be in the cpp.
Including Boost header files only when they are really necessary makes sense. Headers including other headers cause stress to IO and has great impact to compile time. Forward declaration helps to some point, but with Boost it can be real pain.
Using external guards in header files avoids unnecessary loading. Like this:
#ifndef BOOST_SHARED_PTR_HPP_INCLUDED
# include <boost/shared_ptr.hpp>
#endif
Another way to avoid header cascade is to use "pimpl"-idiom, especially when dealing with complex classes. Then complex Boost stuff can be included and used only by that compilation unit. Downside is that interface should be designed so that no Boost specific stuff is required. However, breaking depencies might be a good thing too.
As you mentioned in your post, the boost code contains a lot of template code that require a lot of CPU cycles for compilation. The overhead from multiple header files is very small compared to that.
The first thing you need to do is find out which header file or which line of code is responsible for the delay in compilation. Often it is not the inclusion of the header file, but the usage of one of its classes/functions in your own code that is causing the delay. You can isolate the responsible code by commenting out pieces of your code until compilation is fast again, and then uncommenting your pieces of code until compilation is slow again. Then you can decide whether you want to replace the slow code with something else or not. It's up to you to weigh the pros and cons here or compilation speed vs nifty boost code.
There are a few other things you can do as well:
clean up unneeded include statements, esp in your headers
in your header files, replace includes with forward declarations (where possible)
get a faster computer :D