1

OUTPUT

Fun1 is not fun
9

CODE

#include <stdio.h>

int fun1(void){
    printf("Fun1 is not fun\n");
    return 45%54/5;
}

main()
{
    int c;
    c=fun1();
    printf("%d\n", c);
}  

QUESTION

Why does it output 9 from the 45%54/5? Would this not output 2? The only way I could see this being 9 is by skipping the %, (modulus division operator, right?) then dividing by 5 omitting the 54 completely but that makes no sense to me.

edit: random secondary question. If I name my file test.c, compile it with cc test.c -o test, then type "test", nothing happens. If I compile under any other name than test, it works fine. What gives?

eveo
  • 2,797
  • 15
  • 61
  • 95
  • 1
    Look up the relevant operator precedence. Did this example really have to be that long, just to ask how `45 % 54 / 5` is evaluated? – Kerrek SB Feb 23 '12 at 05:39
  • 1
    Regarding your second question: You have to use `./test`, not `test`. Test is a [unix command](http://en.wikipedia.org/wiki/Test_%28Unix%29). – Zeta Feb 23 '12 at 05:45
  • I am on a unix environment. If I do `cc test.c -o hurrdurr` and type `hurrdurr` everything works fine. – eveo Feb 23 '12 at 05:52

3 Answers3

3
45 % 54 / 5

is

(45 % 54) / 5

Which evaluates as:

45 % 54 = 45
45 / 5  = 9

45 mod 54 is equal to 45. I don't see how you expect to get 2 regardless of how you order them.

Mysticial
  • 464,885
  • 45
  • 335
  • 332
  • Thanks, why is that though? 54 goes into 45 0 times, so there would be no remainder, would it not just be 0? – eveo Feb 23 '12 at 05:41
  • 2
    You're confusing quotient with remainder/modulus. `54` goes into `45` `0` times with a remainder of `45`. – Mysticial Feb 23 '12 at 05:42
  • @soju If it goes in 0 times then everything is the remainder. – RussS Feb 23 '12 at 05:43
  • @soju There is a remainder though, it is 45. 54 goes into 45 0 times with 45 left over. – Hunter McMillen Feb 23 '12 at 05:43
  • Ah okay thanks. So if I have 20 % 7, 7 goes into 20 twice with a remainder of 6. If I have 1 % 99999999, remainder will still be the initial value? I find that odd, thanks for your response. – eveo Feb 23 '12 at 05:45
  • @HunterMcMillen Just got your comment. I understand the logic now. Thank you very much. – eveo Feb 23 '12 at 05:46
  • @Mysticial: I thought it was 45%54/5 = skip the 54, then just do 45/5. – eveo Feb 23 '12 at 05:47
  • @soju Yes, that's correct. `20 % 7 = 6` and `1 % 99999999 = 1` – Mysticial Feb 23 '12 at 05:47
3

The modulus operator has the same precedence as the division operator, so the operations are performed in order from left to right, meaning the modulus is performed first.

45 % 54 = 45

then

45 / 5 = 9

This would be a lot easier to spot if 45 / 5 and 45 % 54 weren't equal, but the numbers here seem coincidental.

Hunter McMillen
  • 59,865
  • 24
  • 119
  • 170
1

The C99 standard has this to say about operator precedence in C99 6.5 Expressions /3 footnote 74):

The syntax specifies the precedence of operators in the evaluation of an expression, which is the same as the order of the major subclauses of this subclause, highest precedence first.

Later on, we see that multiplicative operators are lumped together:

6.5.5 Multiplicative operators
  Syntax
    multiplicative-expression:
      cast-expression
      multiplicative-expression * cast-expression
      multiplicative-expression / cast-expression
      multiplicative-expression % cast-expression

Because they're in the same major section, their precedence is equal, and they're left-associative (a), so the expression:

45 % 54 / 5

is effectively:

  (45 % 54) / 5
= (45) / 5           # 45 / 54 is 0, with a remainder of 45
= 9

That's why you get your answer of 9.


(a) On a side note, I thought I'd found a hole in the C standard since I could find nothing to do with the associativity (left or right) of those operators, whether a/b*c would evaluate as (a/b)*c or a/(b*c).

But, it turns out, the grammar itself (see above) dictates this. Because the grammar states (in part):

multiplicative-expression:
    multiplicative-expression * cast-expression

an expression like a/b*c would have to assign c to the cast-expression and a/b to the multiplicative-expression, evaluating it first.

Hence multiplicative operators are left-associative and the ISO bods, and certain SO bods as well, have once again proved themselves cleverer than I :-)

Community
  • 1
  • 1
paxdiablo
  • 854,327
  • 234
  • 1,573
  • 1,953