Anj Jo
Anj Jo

Reputation: 137

Passing method argument through ternary operator in java

Code:

public class Foo {

    static void test(String s){
        System.out.println("String called");
    }

    static void test(int s){
        System.out.println("int called");
    }

    public static void main(String[] args) throws Exception {

        test(5>8? 5:8);         // Line 1
        test(5>8? "he":"ha");   // Line 2

        test(5>8? 5:"ha");      // Line 3

        System.out.println(5<8? 5:"ha"); //Line 4
    }
}

When I execute this code I get the following Error at Line 3

Foo.java:24: error: no suitable method found for test(INT#1)
                test(5>8? 5:"ha");              // Line 3
                ^

Using similar type in the ternary operator does not give error. But using different types gives error only to the method call test(5>8? 5:"ha"); but it works for the call System.out.println(5<8? 5:"ha");

When I add another overloaded method static void test(Object s){}, then the //Line 3 compiles.

Can anyone please explain me this scenario?

Upvotes: 5

Views: 5866

Answers (3)

Tahir Hussain Mir
Tahir Hussain Mir

Reputation: 2626

When you are calling the function

test(5>8? 5:8);
Method (in present case) is meant to send the parameter hence whole thing inside the parentheses is considered as parameter and there is no appropriate/suitable method to handle such kind of call (whose parameter should be Object) as you are evaluating int and String in one of the statements . Hence the Ternary operator cannot be implemented there.

Hence you can use code like this

(5 > 8) ? test(param1): test(param2);


or create another test method which accepts Object as parameter and then evaluate things inside that test method. like this

void test(Object o){
    //manipulate things here
}

Upvotes: 0

Dawood ibn Kareem
Dawood ibn Kareem

Reputation: 79828

Every expression in Java has a type. There are some complicated rules in the Java Language Specification, in the section on the conditional operator that tell us how to find the type of a conditional expression such as 5 > 8 ? 5 : "ha". But in simple terms, you always get the most specific type that both the second and third arguments are members of.

  • For 5 > 8 ? 5 : 8, both 5 and 8 are int, so this whole expression has type int.
  • For 5 > 8 ? "he" : "ha", both "he" and "ha" are String, so this whole expression has type String.
  • For 5 > 8 ? 5 : "ha", the most specific type that fits both 5 and "ha" is Object. So this whole expression has type Object.

Now since you have versions of test that accept int and accept String, the expressions test ( 5 > 8 ? 5 : 8 ) and test ( 5 > 8 ? "he" : "ha" ) both compile.

But if you don't have a version of test that accepts Object, then test ( 5 > 8 ? 5 : "ha" ) can't compile.

This is an over-simplification. The rules are significantly more complicated than I've described, but this is mostly because they consider the various cases involving null operands, auto-boxing and auto-unboxing.

Upvotes: 8

SoulRayder
SoulRayder

Reputation: 5166

You are calling the method before the expression is evaluated. Since the method doesn't have an overload for test(Object o), it doesn't work.

Call the method after resolving the left side expression.

5>8?test(5):test("ha")

Upvotes: 0

Related Questions