0

I was trying to solve a Counter Game problem:

"Louise and Richard play a game. They have a counter set to N. Louise gets the first turn and the turns alternate thereafter. In the game, they perform the following operations.

  • If N is not a power of 2, they reduce the counter by the largest power of 2 less than N.

  • If N is a power of 2, they reduce the counter by half of N.

  • The resultant value is the new N which is again used for subsequent operations.

The game ends when the counter reduces to 1, i.e., N == 1, and the last person to make a valid move wins.

Given N, your task is to find the winner of the game."

To solve the question, I implemented bit manipulation, and got accepted:

#include <iostream>
#include <cstdio>

int main() {
    long long unsigned int n, tmp;
    int cnt, t;
    scanf("%d", &t);
    while(t--) {
        scanf("%llu", &n), tmp=n;
        cnt=0;
        while(tmp) tmp&=tmp-1, cnt++;
        cnt--;
        while((n&1)==0) n>>=1, cnt++;
        if(cnt%2==0) printf("Richard\n");
        else printf("Louise\n");
    }
    return 0;
}

However, during the coding i coded while(n&1==false) instead of while((n&1)==false), thus could not get desired result. Coding while(!(n&1)) gave expected result, but that(!a instead of a==false) was bad practice due to some sources(I forgot them) I have read online. And I know the difference between while(!n&1) and while(!(n&1)), but I did not know while(n&1==false) and while((n&1)==false). Learnt the latter was and is dissimilar, and may I ask the distinction, please?

garakchy
  • 554
  • 10
  • 19
  • 1
    What's the difference between `1+2*3` and `(1+2)*3`? It's the same problem here. – user2357112 Aug 12 '14 at 05:28
  • usage of `,` operator should be avoided – phuclv Aug 12 '14 at 05:31
  • most compiler warn about the lack of parenthesis – quantdev Aug 12 '14 at 05:36
  • `!a` is usually not considered a bad practice... It may be bad practice for integers in case 0 means "true"/"success" (like `strcmp`). – hyde Aug 12 '14 at 05:36
  • 2
    I don't agree that `!a` was bad practice. Quite the contrary, I would strongly prefer `!a` to `a==false`. Comparing a boolean (a) to a boolean (false) just to get a boolean that you had in the first place seems rather strange to me. The 'not' operator ! on the other hand has clear semantics. – Ferdinand Beyer Aug 12 '14 at 05:39

3 Answers3

4

As you can see here, the precedence of == is above the precedence of &.

Therefore n&1==false is interpreted as n&(1==false) not (n&1)==false, so you need the parentheses.

4

This is considered by many a design mistake of C.

While it's natural that a logical-and operation should have lower precedence than equality comparison the same is much more questionable for bitwise-and because bitwise operations are naturally closer to math operations.

The same design error has been inherited by C++ for backward compatibility.

A good rule is always parenthesize bitwise operations to avoid surprises.

6502
  • 112,025
  • 15
  • 165
  • 265
2

== has higher priority in C++ than & (source).

Thus while(n&1==false) is treated as while (n & (1 == false)) which actually is while (n & 0).

FreeNickname
  • 7,398
  • 2
  • 30
  • 60