Most Microsoft run-time library routines are compiled or assembled functions, but some routines are implemented as macros. When a header file declares both a function and a macro version of a routine, the macro definition takes precedence, because it always appears after the function declaration. When you invoke a routine that is implemented as both a function and a macro, you can force the compiler to use the function version in two ways:
#include <ctype.h>
a = toupper(a); //use macro version of toupper
a = (toupper)(a); //force compiler to use function version of toupper
#include <ctype.h>
#undef toupper
If you need to choose between a function and a macro implementation of a library routine, consider the following trade-offs:
#define toupper(c) ( (islower(c)) ? _toupper(c) : (c) )
In the following example, the toupper macro produces a side effect:
#include <ctype.h>
int a = 'm';
a = toupper(a++);
The example code increments a
when passing it to toupper. The macro evaluates the argument a++
twice, once to check case and again for the result, therefore increasing a
by 2 instead of 1. As a result, the value operated on by islower differs from the value operated on by toupper.