4

I'm studying some Java at the moment at I've come across the following piece of code. I understand how the typical ternary operator (e.g. the line beginning with "boolean a" below), but I can't understand how to read the expression on the line beginning with "boolean b". Any help on how to read this line would be much appreciated! Thanks!

public class Ternary{
    public static void main (String[] args){
        int x = 10;
        int i = 2;
        boolean a = x > 10 ? true: false;
        boolean b = a = true ? ++i > 2 ? true:false:false;
        System.out.print(b);
    }
}
2
  • 2
    Go through the details of operator precedence: docs.oracle.com/javase/tutorial/java/nutsandbolts/…. I feel for you--that code is abstruse. Commented Mar 3, 2014 at 15:54
  • Ternary operator has the following format (condition ? result when condition is true : result when condition is false). So here, we define the boolean a, then assign it the result of the ternary operator. Commented Mar 3, 2014 at 15:57

8 Answers 8

6

Break it up like this:

true ? (++i > 2 ? true 
                : false)
     : false;

So here the testing condition is always set to true. So the branch of the ternary that executes is the ++i > 2 ? true : false part.

This simply checks to see if after incrementing, i is greater than 2. If so, it will return true. Otherwise it will return false.

This whole expression is actually needlessly complex. It can simply be written as such:

boolean b = a = (++ i > 2);

However, the code is probably logically incorrect since this abstruse expression doesn't make that much sense. Since the previous line sets the value of a, I'm assuming that the next line actually intends to test a. So the actual intent might be:

boolean b = a == true ? ++i > 2 ? true : false : false; //notice the ==

In which case you can break it up as:

(a == true) ? (++i > 2 ? true
                       : false)
            : false;

But you don't need to actually do a == true since a is already a boolean, so you can do:

a ? (++i > 2 ? true
             : false)
  : false;

Here, it checks to see if a is true. If it is, it performs the check we already went over (i.e., to see if the incremented value of i is greater than 2), otherwise it returns false.

But even this complicated expression can be simplified to just:

boolean b = a && (++i > 2);
Sign up to request clarification or add additional context in comments.

5 Comments

What about the last false? Does it do a truth table T v F = T?
The last false would never be evaluated in this case since the test is always true.
Thanks for your explanation Vivin (and everyone else). The code actually came from a sample OCJA exam which is possibly explains why it is written so needlessly complex. Thanks again!
lol now i had -3 on my deleted question for being the first one to mention b = a = true is incorrect. And see your comment below Rohit Jain's answer..
@Zefnus I meant "correct" as in the code would compile. But yeah, it doesn't really make sense.
1

Ah! Never write code like that. But I would assume that is not written by you. But you can read it like this:

// I assume that's `a == true` instead of `a = true`
boolean b = a == true ? (++i > 2 ? true : false)
                      : false;

which can be broken further as:

// a == true is better written as just `a`. You shouldn't do boolean comparison
// like that.
boolean b = a ? (++i > 2) : false;

// If that is really a = true, then you can break it as:
boolean b = a = true ? (++i > 2) : false;

which can be further broken down as:

// If that is `a == true`
boolean b = a && (++i > 2)

// If that is really a = true, then you can break it as:
boolean b = a = (++i > 2);

Also, the first assignment:

boolean a = x > 10 ? true: false;

can also be written as:

boolean a = x > 10;

7 Comments

I don't think this is correct. The boolean b = a = true is correct; it is just assigning the result to both a and b.
a == true is not too nice, but it does not assign true to a.
FYI, IntelliJ simplified it to boolean b = a = ++i > 2;.
@VivinPaliath Updated the answer for that case, but I suspect it really meant that. That would be strange code in that case.
@GáborBakos I know a == true is not too nice. Please see my updated answer.
|
1
boolean nu = f=='f' && t=='f'; //0
boolean ei = f=='f' && t=='t'; //1
boolean zw = f=='t' && t=='f'; //2
boolean dr = f=='t' && t=='t'; //3
System.out.println( nu ? 0 : ei ? 1 : zw ? 2 : dr ? 3 : "invalid");

Comments

0

In boolean b = a = true ? ++i > 2 ? true:false:false; the following happens:

a = true

This will give a true value and evaluate to true.

Than we get another condition, ++i > 2 from ++i > 2 ? true:false, which will be also true in this case. The outcome will be true.

Comments

0

Ternary operators are

condition then true or false

The condition is always true (because a equals true).

Then the result is true because ++i is greater than 2 (it's 3).

Therefore, it assigns true to b. If the condition was false, it would assign false. That false would be assigned from the last false.

Comments

0

It would help if you could use parentheses and review that code as follows;

boolean b = a = (true ? (++i > 2 ? true : false) : false);

You can think it as:

if (true) // # If Number:1
{
    if (++i > 2) // # If Number:2
    {
        a = true;            
    }
    else { a = false; }
}
else { a = false; }

Where if(true) is a Tautology and If Number:2 will always be executed. Therefore; it becomes;

if (++i > 2)
{
    a = true;            
}
else { a = false; }

Which can be evaluated to; a = (++i > 2) ? true : false); and which becomes: a = ++i > 2 as a result b = a which is ++i > 2.

Comments

0

With some guesses at what is being attempted and some renaming of variables, and assuming the a = true was meant to be a == true you get:

    boolean failed = result > 10 ? true: false;
    boolean b = failed ? ++retries > 2 ? true:false:false;

This can then be tidied up to the much more logical:

    boolean failed = result > 10;
    boolean giveUp = failed && ++retries > 2;

Comments

0

Horrible code!

There are a couple of clues that the b = a = true ? ... should be b = a == true ? ..., since otherwise the previous line is a useless assignment (a is never read), and the final false of the line becomes unreachable code. The compiler will tell you that.

I'm going to answer assuming a corrected == - but you'll know whether it was a typo on your part, an unreliable source, or a 'spot the bug' test, and be able to use the same techniques on whatever code you like.

The trick is to refactor it step by step. First add brackets and indentation based on precedence rules.

 b = a == true ? ++i > 2 ? true:false:false;
 ... becomes ...
 b = (a == true) 
          ? (++i > 2 ? true:false)
          :false;

Next note that:

  • a == true is equivalent to a.
  • boolean x = a ? true : false; is equivalent to boolean x = a.

Therefore:

 b = a
     ? (++i > 2)
     :false;

or:

 b = a && ( ++i > 2 );

If this is "serious" code, the way to approach this would be to write a set of unit tests that cover all the possible input cases. Then make these refactorings one at a time, each time re-running the tests to ensure that you've not changed the behaviour of the code.

Notice that there are no true or false literals in the reduced form. Seeing boolean literals in a ternary operation -- or indeed, ternary expressions for boolean values at all -- is a code smell, since the non-ternary version is usually simpler and clearer.

Ternary expressions are very useful for their intended purpose, which is mapping boolean conditions to non-boolean outputs:

 shippingPrice = orderTotal >= freeShippingThreshold ? 0 : getStandardShipping();

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.