-3

I have this code...

class Test {

    public static void main(String[] args) {
        Boolean mySuperBoolean = Boolean.FALSE;

        System.out.print("a");
        if (mySuperBoolean = Boolean.TRUE) {
            System.out.print("b");
        }

        System.out.print("c");
    }
}

I am new to Java, but I knew single equal (=) is used to assign. And double equals (==) is used to check if object is referred to the same location in memory. However, in this case I do not understand how the 'b' is being printed with a single equals, but I understand changing it to a double equals sign will not print it out

Harry
  • 1
  • 1
  • `==` not `=` in the if – GBlodgett Feb 04 '19 at 14:03
  • 1
    `mySuperBoolean = Boolean.TRUE` should be `mySuperBoolean == Boolean.TRUE`, – forpas Feb 04 '19 at 14:03
  • 1
    This is because `mySuperBoolean = Boolean.TRUE` returns true – Ratish Bansal Feb 04 '19 at 14:04
  • [Using the assignment operator instead of the equality operator](https://www.quirksmode.org/blog/archives/2008/01/using_the_assig.html) – Ole V.V. Feb 04 '19 at 14:17
  • Somehow related: [Return value of assignment operation in Java](https://stackoverflow.com/questions/38163938/return-value-of-assignment-operation-in-java) – Ole V.V. Feb 04 '19 at 14:18
  • I have voted to reopen since this question is not about a simple error and its correction, but about *understanding* how it can be that the version with single `=` behaves the way it does. – Ole V.V. Feb 04 '19 at 15:03

4 Answers4

2

Assignment is an expression which resolves to whatever was assigned, in this case
(mySuperBoolean = Boolean.TRUE) is an expression which resolves to Boolean.TRUE.

This is really only useful in a few specific situations. One such case is the following idiom:

String line;
while ((line = readLine()) != null) {
    //...
}

Or even

i = j = k = 0; // equal to: i = (j = (k = 0))

It's a controversial feature because it allows probable bugs such as yours to compile successfully. To mitigate this, some people will invert the operands (a "yoda condition"):

if (Boolean.TRUE == mySuperBoolean)

This works because if I forget the second equals then the compiler will throw an error because Boolean.TRUE is final and cannot be assigned to.

Michael
  • 41,989
  • 11
  • 82
  • 128
  • 1
    This is the well explained answer, thank you. I don’t hink I ever use the value of an assignment for anything, your example is idiomatic, though. The other example goes like `i = j = k = 0;`, which sets al of `i`, `j` and `k` to 0. Instead of `if (mySuperBoolean == Boolean.TRUE)` I strongly recommend just `if (mySuperBoolean)`, it also evades the issue of the forgotten extra equals sign. – Ole V.V. Feb 04 '19 at 14:22
  • 1
    `if (mySuperBoolean)` is not always possible, if `mySuperBoolean` were a nullable Boolean. – Michael Feb 04 '19 at 14:26
  • Good point, @Michael. However, that’s subtle, there’s something dangerous about nullable `Boolean` as a whole. But if you insist, make the null check explicit: `if (mySuperBoolean != null && mySuperBoolean)`. Would be my recommendation. The intention and everything is clearer than in the Yoda condition case. – Ole V.V. Feb 04 '19 at 15:00
1

if (mySuperBoolean = Boolean.TRUE) will assign Boolean.TRUE to your mySuperBoolean variable and the condition will evaluate to true, hence whatever is inside your if it will always execute

nullPointer
  • 4,419
  • 1
  • 15
  • 27
1

The result of the assignment operator = will be the assigned value. So if (mySuperBoolean = Boolean.TRUE) will always evaluate to true.

João Dias Amaro
  • 511
  • 6
  • 14
0

In essence, what happens here boils down to:

if (Boolean.TRUE) {
  System.out.print("b");
}

That assignment puts TRUE into the variable, the variable is boolean, and checked for its current value, end of story.

GhostCat
  • 137,827
  • 25
  • 176
  • 248