Preprocessor
Before compilation, every .cpp file goes through preprocessing.
Preprocessor makes textual changes to the code, but it does not modify the original files.
The result of preprocessing is a translation unit, meaning a single .cpp file after directives such as #include have been expanded.
Preprocessor directive starts with # and ends at the newline, not with a semicolon.
#include <iostream>
#define MY_NAME
#ifdef MY_NAME
#endif
#include inserts the contents of the specified file in place of the directive:
#include "add.h"
#define creates a macro.
#define macros work from the place of definition to the end of the current file.
If a macro is in a header, it also reaches files that include that header.
That is powerful, and also exactly the kind of thing that can make debugging feel cursed.
Conditional compilation#
Conditional compilation means including or excluding parts of code before compilation.
#ifdef and #ifndef work like conditions for the preprocessor:
#ifndef MY_NAME
std::cout << "End!\n";
#endif
This code is included in compilation only if the MY_NAME macro does not exist.
#if 0 ... #endif can temporarily exclude a block of code from compilation.
The same mechanism is used in header guards.
This is why preprocessor belongs near headers, even if at first it looks like suspicious magic.