Collections Arrays你会用么?

本文探讨了Java中Collections和Arrays工具类的高级应用技巧,包括emptyList的特性、toArray方法的不同用法以及asList方法的注意事项。文章通过具体代码示例展示了如何正确使用这些方法避免常见的陷阱。

title: Collections Arrays你会用么? tags:

  • Collections
  • Arrays
  • toArray
  • asList
  • jcf categories: jcf date: 2017-12-08 13:20:26

背景

JDK给我们提供了一些工具类 用来操作集合等。

通常来说命名规则就是XXXXs 比如Collections 比如Arrays

看到部分同学使用如下

遍历时这样

测试

    public class CollectionsTest {
        @Test(expected = UnsupportedOperationException.class)
        public void testEmptyCollections() {
            List<TbUser> userList = Collections.emptyList();
            userList.add(new TbUser());
        }
     
        @Test
        public void testToArray() {
            List<String> list = Lists.newArrayList("1", "2", "3");
            Object[] objects = list.toArray();
        }
     
        @Test
        public void testToArray2() {
            List<String> list = Lists.newArrayList("1", "2", "3");
            String[] strings = list.toArray(new String[list.size()]);
        }
复制代码

解读EmptyList是无法add会抛出

UnsupportedOperationException
复制代码

因为emptyList如下

    private static class EmptyList<E>
        extends AbstractList<E>
        implements RandomAccess, Serializable {
        private static final long serialVersionUID = 8842843931221139166L;
     
        public Iterator<E> iterator() {
            return emptyIterator();
        }
        public ListIterator<E> listIterator() {
            return emptyListIterator();
        }
     
        public int size() {return 0;}
        public boolean isEmpty() {return true;}
     
        public boolean contains(Object obj) {return false;}
        public boolean containsAll(Collection<?> c) { return c.isEmpty(); }
     
        public Object[] toArray() { return new Object[0]; }
     
        public <T> T[] toArray(T[] a) {
            if (a.length > 0)
                a[0] = null;
            return a;
        }
     
        public E get(int index) {
            throw new IndexOutOfBoundsException("Index: "+index);
        }
     
        public boolean equals(Object o) {
            return (o instanceof List) && ((List<?>)o).isEmpty();
        }
     
        public int hashCode() { return 1; }
     
        @Override
        public boolean removeIf(Predicate<? super E> filter) {
            Objects.requireNonNull(filter);
            return false;
        }
        @Override
        public void replaceAll(UnaryOperator<E> operator) {
            Objects.requireNonNull(operator);
        }
        @Override
        public void sort(Comparator<? super E> c) {
        }
     
        // Override default methods in Collection
        @Override
        public void forEach(Consumer<? super E> action) {
            Objects.requireNonNull(action);
        }
     
        @Override
        public Spliterator<E> spliterator() { return Spliterators.emptySpliterator(); }
     
        // Preserves singleton property
        private Object readResolve() {
            return EMPTY_LIST;
        }
    }
复制代码

当使用toArray时需要最好传入指定类型的数组【否则类型不对】

    public class ArraysTest {
     
        @Test
        public void testAsList0() {
            Set<String> set = Sets.newSet("a", "b", "c");
     
            List strList = Arrays.asList(set);
     
        }
     
        @Test
        public void testAsList1() {
            Set<String> set = Sets.newSet("a", "b", "c");
            List<Set<String>> strSetList = Arrays.asList(set);
     
        }
     
        @Test
        public void testAsList2() {
            String[] strs;
            strs = new String[]{"a", "b", "c"};
            List strings = Arrays.asList(strs);
            Assert.assertEquals(strings.size(), 3);
     
        }
     
        @Test
        public void testAsList3() {
            Object strs;
            strs = new String[]{"a", "b", "c"};
            List strings = Arrays.asList(strs);
            Assert.assertEquals(strings.size(), 1);
     
        }
     
     
        @Test(expected = UnsupportedOperationException.class)
        public void testAsList4() {
            List<String> list = Arrays.asList("1", "2", "3");
            list.add("4");
     
        }
     
        @Test(expected = ClassCastException.class)
        public void testAsList5() {
            List<Integer> list = new ArrayList<>();
            list.add(1);
            List list2 = list;
            list2.add("1223");
            for (Integer integer : list) {
                System.out.println(integer);
            }
     
     
        }
    @Test
    public void testAsList6() {
        Object strs;
        strs = new String[]{"a", "b", "c"};
        List strings = Arrays.asList((String[])strs);
        Assert.assertEquals(strings.size(), 3);
     
    }
     
    }
复制代码

解读

指的注意的是asList接受可变参数 【及其容易引起问题】

比如testAsList2 testAsList3 testAsList6

主要在于声明等不同就会造成最终list的size完全不同!慎用可变参数!

Arrays.asList返回ArrayList

    /**
     * Returns a fixed-size list backed by the specified array.  (Changes to
     * the returned list "write through" to the array.)  This method acts
     * as bridge between array-based and collection-based APIs, in
     * combination with {@link Collection#toArray}.  The returned list is
     * serializable and implements {@link RandomAccess}.
     *
     * <p>This method also provides a convenient way to create a fixed-size
     * list initialized to contain several elements:
     * <pre>
     *     List<String> stooges = Arrays.asList("Larry", "Moe", "Curly");
     * </pre>
     *
     * @param <T> the class of the objects in the array
     * @param a the array by which the list will be backed
     * @return a list view of the specified array
     */
    @SafeVarargs
    @SuppressWarnings("varargs")
    public static <T> List<T> asList(T... a) {
        return new ArrayList<>(a);
    }
复制代码

稍不注意就会踩到大坑!这个ArrayList是李鬼 全称是java.util.Arrays.ArrayList

该'arrayList' 不支持正常的add操作会抛出UnsupportedOperationException 【见testAsList4】

List的泛型完全支持用户想在Integer的List中放入String 【多么变态的需求】一个朋友圈泛型问题引发的“案子” 不过真的这么做了 在取的时候就容易踩到巨坑!

还是别了吧!

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值