开发者

Generic Type toArray and asList

I am trying to understand generics and I purposely want to generate a classcastexception, however, i instead get an arraystoreexception on the first attempt.

    static <E> E reduce(List<E> list, Function<E> f, E initVal) {

    E[] snapshot = (E[]) list.toArray();

    Object[] o = snapshot;
    o[0] = new Long(1);

    E result =  initVal;
    for (E e : snapshot)
        result = f.apply(result, e);


    return result;
}


private static final Function<Integer> SUM = new Function<Integer>(){
    public Integer apply(Integer i1, Integer i2) {
        return i1 + i2;
    }
};

public static void main(String[] args) {
    List<Integer> intList = Arrays.asList(2, 7);
    System.out.println(reduce(intList, SUM, 0));
}

On the second attempt.. I correctly get a ClassCastException using this...

public static void main(String[] args) {
    List<Integer> intList1 = Arrays.asList(2, 7);
    List<Integer> intList = new ArrayList<Integer>(intList1);
    System.out.println(reduce(intList, SUM, 0));
}

What is the diff开发者_高级运维erence?


It appears to me that the List instance produced by Arrays.asList() does not properly implement the contract of the toArray() method. From List.toArray() javadoc:

Note that toArray(new Object[0]) is identical in function to toArray(). 

However note the following test:

public static void main(String... args) {
  System.out.println(Arrays.asList(2, 7).toArray());
  System.out.println(Arrays.asList(2, 7).toArray(new Object[0]));
}

and output:

[Ljava.lang.Integer;@3e25a5
[Ljava.lang.Object;@19821f

Note that according to the javadoc, toArray() should produce an array of type Object[], but Arrays.<E>asList().toArray() instead produces an array of type E[].

The reason you get an ArrayStoreException is because your array is of type Integer[] when it should be of type Object[].


I don't know why you're creating an array. Just do this:

static <E> E reduce(List<E> list, Function<E> f, E initVal) {
    for (E e : list)
        initVal = f.apply(initVal, e);
    return initVal;
}

See: KISS principle

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜