Output of List varies while using loops on Varargs

Viewed 63

Outputs of the code is varies on iterating with Varargs. Please let me know what is the reason for different outputs.

public class Demo {

    public static void main(String[] args) {
        
        Integer[] a = new Integer[]{1, 2, 3};
        Integer[] b = new Integer[]{4, 5, 6};
        
        
        List<Object> list1=new ArrayList<>();
        addAllObj1(list1, a,b);
        System.out.println(list1); //[[Ljava.lang.Integer;@24d46ca6, [Ljava.lang.Integer;@4517d9a3]
        
        List<Object> list2=new ArrayList<>();
        addAllObj2(list2, a,b);
        System.out.println(list2); //[1, 2, 3, 4, 5, 6]
    }
    
    private static void addAllObj1(List<Object> list, Object[]... arr) {
        for(Object o:arr) {
            Collections.addAll(list, o);
        }
    }
    
    private static void addAllObj2(List<Object> list, Object[]... arr) {
        Collections.addAll(list, arr[0]);
        Collections.addAll(list, arr[1]);
    }

}

Thanks for your Help!

1 Answers

I am sorry for posting a wrong answer, but I think I found the solution now within the Java Specification. Here is how I understand it:

I think the following explains it:

private static void addAllObj2(List<Object> list, Object[]... arr) {
    Object o = arr[0];
    Collections.addAll(list, o);
    Collections.addAll(list, arr[1]);
}

returns:

[[Ljava.lang.Integer;@75a1cd57, 4, 5, 6]

The line with index 1 does work, because during runtime, the jvm evaluates the arity parameters the the type of the input will not be rewritten The conversion to Integer apparently is possible. (I guess the type of b will not be changed)

In the line with index 0, the type will be evaluated and rewritten due to Type Erasure, as it will be stored as the Object o. The Type of the Object o and a (Integer[]) is not the same, therefore erasure takes place and it will be converted to an Object, hence the reference name.

This process apparently only takes place with arity parameters, as without:

 public static void main(String[] args) {
    List<Object> list3 = new ArrayList<>();
    addAllObj3(list3, trePConcat(a, b));
    System.out.println(list3);

    
}

private static void addAllObj3(List<Object> list, Object[] arr) {
    Collections.addAll(list, arr[0]);
    Collections.addAll(list, arr[1]);
    {
        try {
            Thread.sleep(10);
        } catch (InterruptedException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
    }
}

private static Object[] trePConcat(Object[]... arr) {
    return arr;
}

returns

[[Ljava.lang.Integer;@75a1cd57, [Ljava.lang.Integer;@3d012ddd]
Related