Reputation: 981
Why is the answer for the below code 16? Can anybody explain the working of this program?
#define SQUARE(n) n*n
void main()
{
int j;
j =16/SQUARE(2);
printf("\n j=%d",j);
getch();
}
If we write the same code like below, then the answer is 4:
//the ans is 4 why?
#include<stdio.h>
#include<conio.h>
#define SQUARE(n) n*n
void main()
{
int j;
j =16/(SQUARE(2));
printf("\n j=%d",j);
getch();
}
Upvotes: 7
Views: 1862
Reputation: 924
It’s because whenever a macro name is used, it is replaced by the contents of the macro. It’s the simple rule of the workings of a macro.
Case 1: result 16
define SQUARE(n) n*n
void main()
{
int j;
j = 16/SQUARE(2);
printf("\n j=%d", j);
getch();
}
It gets expanded as below:
j = 16/SQUARE(2);
So in place of SQUARE(2), it will replace 2*2, because the macro is SQUARE(n) n*n
j = 16/2*2
j = (16/2)*2
j = 8*2
j =16
Case 2: result 4
define SQUARE(n) n*n
void main()
{
int j;
j = 16/(SQUARE(2));
printf("\n j=%d", j);
getch();
}
It gets expanded as below:
j = 16/(SQUARE(2));
So in place of SQUARE(2), it will replace 2*2, because the macro is SQUARE(n) n*n
j = 16/(2*2)
j = 16/(4)
j = 4
Upvotes: 0
Reputation: 5869
Because the macro will be expanded as:
j = 16/2*2;
The pre-compiler does not do any processing on the expansion. It places the expanded macro in your code as it is. Since you have not parenthesized the replacement text it wont do it for you in the main code as well. Make it :
#define SQUARE(n) ((n)*(n))
Upvotes: 2
Reputation: 107191
The Expansion of macro will be like:
j = 16/SQUARE(2);
j = 16/2*2;
Which is equal to : j = (16/2)*2;
Means j = 16;
and :
j = 16/(SQUARE(2));
j = 16/(2*2);
Which is equal to : j = 16/4;
Means j = 4;
Upvotes: 2
Reputation: 9997
The first example is evaluated as:
16 / 2 * 2
(16 / 2) * 2
8 * 2
16
The second example is evaluated as:
16 / (2 * 2)
16 / 4
4
Add parenthesis to you preprocessor statement to control the order of operations:
#define SQUARE(n) ((n)*(n))
The outer parenthesis in ((n)*(n)) ensure that n is squared before any outside operation is performed. The inner parenthesis (n) ensure that n is correctly evaluated in cases where you pass an expression to SQUARE like so:
16 / SQUARE(2 * 2)
16 / ((2 * 2)*(2 * 2))
16 / (4 * 4)
16 / 16
1
Upvotes: 1
Reputation: 399949
The preprocessor just replaces the text, exactly as written.
So, the macro call SQUARE(2)
becomes literally 2*2
.
In your case, that means the whole expression becomes 16/2*2
, which because of C's precedence rules evaluates to (16/2)*2, i.e. 16.
Macros should always be enclosed in parenthesis, and have each argument enclosed as well.
If we do that, we get:
#define SQUARE(n) ((n) * (n))
which replaces to 16/((2) * (2))
, which evaluates as 16/4, i.e. 4.
The parens around each argument makes things like SQUARE(1+1)
work as expected, without them a call such as 16/SQUARE(1+1)
would become 16/(1+1*1+1)
which is 16/3
, i.e. not at all what you'd want.
Upvotes: 16
Reputation: 72279
This prevents erroneous expansions like:
#define SQUARE(x) x*x
-SQUARE(5,5)
// becomes -5 * 5
This prevents a different type of problems:
#define SQUARE(x) x*x
SQUARE(5+2)
// becomes 5 + 2*5 + 2
Hence the correct way is to write it like this:
#define square(n) ((n)*(n))
-SQUARE(5+2)
// becomes -((5+2)*(5+2))
Using macros as functions is discouraged though (guess why), so use a function instead. For instance:
inline double square(n) { return n*n; }
Upvotes: 3
Reputation: 300719
You need to define your macro with insulating parentheses, like so:
#define SQUARE(n) ((n)*(n))
Otherwise
j = 16/SQUARE(2);
expands to
j = 16 / 2 * 2; which is equivalent to (16 / 2) * 2
When what you want is
j = 16 / (2 * 2);
Upvotes: 3
Reputation: 67
Order of operations. Your expression is evaluating to:
j = 16 / 2 * 2
which equals 16. Make it:
#define SQUARE(n) (n*n)
which will force the square to be evaluated first.
Upvotes: 3