Doublespeed
Doublespeed

Reputation: 1173

Having trouble with the mod operator; I'm not getting the result I'm expecting

There is a puzzle on codingbat.com that seemed quite trivial but when I solved it and submitted, it was marked wrong when the argument 45 or 15 was passed in to the method. What am I doing wrong here in my logic to the following question?

Return true if the given non-negative number is a multiple of 3 or 5, but not both. Use the % "mod" operator -- see Introduction to Mod

My solution:

public Boolean old35(int n) {
  if( n % 3 == 0 || n % 5 == 0 && !(n % 3 == 0 && n % 5 == 0) ){
    return true;
  }

  return false;
}

Codingbat's solution that makes no sense to me at all:

public Boolean old35(int n) {
    return n % 3 == 0 ^ n % 5 == 0;
}

Upvotes: 2

Views: 1946

Answers (3)

Waz
Waz

Reputation: 11

return (n%3 == 0 || n%5 == 0) && !(n%3 == 0 && n%5 == 0);

You can check both conditions and then pass the results of those conditions through an AND gate (&&).

Upvotes: 1

rgettman
rgettman

Reputation: 178263

The && operator takes precedence over ||, so it takes place after !(n % 3 == 0 && n % 5 == 0) but before the or ||. With 45, it's true that it's a multiple of 3 and 5, so the ! returns false. It's a multiple of 5, so true & false yields false. It's a multiple of 3, so true or false yields true, which is incorrect according to the requirements.

You can correct your solution by inserting parentheses to force the || before the first &&:

//  v                          v
if( ( n % 3 == 0 || n % 5 == 0 ) && !(n % 3 == 0 && n % 5 == 0) ){

Codingbat's solution uses the XOR operator, ^. This operator means either one or the other is true, but not both, which fits the requirements exactly. Also, there is no reason for the if; you can return the boolean expression directly.

Upvotes: 6

Paul Boddington
Paul Boddington

Reputation: 37645

Your solution is almost right. You just need brackets:

if((n % 3 == 0 || n % 5 == 0) && !(n % 3 == 0 && n % 5 == 0) )

Without brackets it is treated as

if( n % 3 == 0 || (n % 5 == 0 && !(n % 3 == 0 && n % 5 == 0)) )

^ is exclusive or. x ^ y means either x or y is true, but not both.

Upvotes: 2

Related Questions