May 11, 2021 C
The C preprocessor is not part of the compiler, but it is a separate step in the compilation process. I n short, the C preprocessor is nothing more than a text replacement tool that instructs the compiler to complete the required pre-processing before actually compiling. We'll short C Preprocessor as CPP.
All preprocessor commands start with a hashtag. I t must be the first non-empty character, and in order to enhance readability, preprocessor instructions should start with the first column. Here's a list of all the important preprocessor instructions:
instruction | describe |
---|---|
#define | Define macro |
#include | Contains a source code file |
#undef | Cancel the defined macro |
#ifdef | Returns true if the macro has been defined |
#ifndef | If the macro is not defined, return true |
#if | If a given condition is true, compile the following code |
#else | #iF alternative |
#elif | If the previous #IF is not true, the current condition is true, then compile the following code. |
#endif | End a # ix ... # Else Condition Compiling Block |
#error | Output error messages when you encounter a standard error |
#pragma | Use normalization methods to publish special commands to the compiler into the compiler |
Analyze the following examples to understand the different instructions.
#define MAX_ARRAY_LENGTH 20
This instruction tells the CPP to replace all MAX_ARRAY_LENGTH with 20. Use #define to define constants to enhance readability.
#include <stdio.h> #include "myheader.h"
These instructions tell the CPP to get stdio.h from the System Library and add text to the current source file. The next line tells the CPP to get myheader.h from the local directory and add content to the current source file.
#undef FILE_SIZE #define FILE_SIZE 42
This instruction tells the CPP to cancel the FILE_SIZE and define it as 42.
#ifndef MESSAGE #define MESSAGE "You wish!" #endif
This instruction tells the CPP that MESSAGE is defined only if it is not defined.
#ifdef DEBUG /* Your debugging statements here */ #endif
This instruction tells the CPP that if DEBUG is defined, the processing statement is executed. A t compile time, this instruction is useful if you pass the -DDEBUG switch to the gcc compiler. It defines DEBUG, which allows you to turn debugging on or off at any time during compilation.
ANSI C defines many macros. You can use these macros in programming, but you cannot modify them directly.
Macro | describe |
---|---|
__DATE__ | The current date, a character constant represented in "mmm DD YYYY" format. |
__TIME__ | Current time, a character constant represented in "HH: mm: SS" format. |
__FILE__ | This will contain the current file name, a string constant. |
__LINE__ | This will contain the current line number, a decimal constant. |
__STDC__ | When the compiler is compiled in an ANSI standard, it is defined as 1. |
Let's try the following example:
#include <stdio.h>
int main()
{
printf("File :%s\n", __FILE__ );
printf("Date :%s\n", __DATE__ );
printf("Time :%s\n", __TIME__ );
printf("Line :%d\n", __LINE__ );
printf("ANSI :%d\n", __STDC__ );
}
When the above code (in the file test .c) is compiled and executed, it produces the following results:
File :test.c Date :Jun 2 2012 Time :03:36:24 Line :8 ANSI :1
The C preprocessor provides the following operators to help you create macros:
A macro is usually written on a single line. H owever, if the macro is too long to fit on a single line, the macro continuation operator is used. For example:
#define message_for(a, b) \ printf(#a " and " #b ": We love you!\n")
In a macro definition, when you need to convert the parameters of a macro to a string constant, you use the string constant operator. T he operator used in macros has a specific list of parameters or parameters. For example:
#include <stdio.h>
#define message_for(a, b) \
printf(#a " and " #b ": We love you!\n")
int main(void)
{
message_for(Carole, Debra);
return 0;
}
When the above code is compiled and executed, it produces the following results:
Carole and Debra: We love you!
The tag paste operator within the macro definition merges two parameters. I t allows two separate tags in the macro definition to be merged into one tag. For example:
#include <stdio.h>
#define tokenpaster(n) printf ("token" #n " = %d", token##n)
int main(void)
{
int token34 = 40;
tokenpaster(34);
return 0;
}
When the above code is compiled and executed, it produces the following results:
token34 = 40
This is how this happens because this instance produces the following actual output from the compiler:
printf ("token34 = %d", token34);
This example demonstrates that token##n is connected to token34, where we use the string normalization operator and the tag paste operator .
The preprocessor defined operator is used in constant expressions to determine whether an identifier has been defined using #define of . I f the specified identifier is defined, the value is true (non-zero). I f the specified identifier is not defined, the value is false (zero). The following example demonstrates the use of the defined() operator:
#include <stdio.h>
#if !defined (MESSAGE)
#define MESSAGE "You wish!"
#endif
int main(void)
{
printf("Here is the message: %s\n", MESSAGE);
return 0;
}
When the above code is compiled and executed, it produces the following results:
Here is the message: You wish!
A powerful feature of CPP is that you can simulate functions using paramethic macros. For example, the following code calculates the square of a number:
int square(int x) { return x * x; }
We can use macros to rewrite the code above, as follows:
#define square(x) ((x) * (x))
Before you can use a macro with parameters, you must use #define the directive. T he list of parameters is enclosed in parentheses and must be immediately behind the macro name. S paces are not allowed between the macro name and the opening parenthesis. For example:
#include <stdio.h>
#define MAX(x,y) ((x) > (y) ? (x) : (y))
int main(void)
{
printf("Max between 20 and 10 is %d\n", MAX(10, 20));
return 0;
}
When the above code is compiled and executed, it produces the following results:
Max between 20 and 10 is 20