码迷,mamicode.com
首页 > 编程语言 > 详细

java-集合类(二)

时间:2015-08-18 12:07:00      阅读:146      评论:0      收藏:0      [点我收藏+]

标签:集合   java   

使用场景

1.多线程

(1)在jdk1.5之前原始的集合类中,只有vector、stack、hashtable、enumeration等是线程安全的,其他的都是非线程安全的。
非线程安全的集合在多线程操作中,会出现脏数据,如

final List<String> tickets = new ArrayList<String>();
        for (int i = 0; i < 100000; i++) {
            tickets.add("NO," + i);
        }
        System.out.println("start1...");
        for (int i = 0; i < 5; i++) {
            Thread thread = new Thread() {
                public void run() {
                    while (true) {
                        if (tickets.size() > 0)
 System.out.println("thread:"+Thread.currentThread().getId()+" "+ tickets.remove(0));
                        else
                            break;
                    }
                }
            };
            thread.start();
        }

运行结果:

......
thread:13 NO,98687
thread:12 NO,96534
thread:10 NO,96534
thread:10 NO,98687
......
thread:10 null
thread:12 null

线程不安全导致多个线程调用 remove 时同时操作 List 进行读写。
ArrayList修改成 Stack,问题解决。
(2)线程安全的集合也需要遵守fail-fast的检测机制,即在迭代的时候,不能修改集合的元素。一旦发现违反这个规定就会抛出ConcurrentModificationException异常。如需在迭代过程中修改元素,需要对迭代和修改加同步锁。
如下面代码将出现ConcurrentModificationException异常。

final List<String> tickets = Collections
                .synchronizedList(new ArrayList<String>());
        for (int i = 0; i < 100; i++) {
            tickets.add("NO," + i);
        }
        System.out.println("start1...");
        for (int i = 0; i < 5; i++) {
            Thread thread = new Thread() {
                public void run() {
                    while (true) {
                        if (tickets.size() > 0)
                            System.out.println("thread:"
                                    + Thread.currentThread().getId() + " "
                                    + tickets.remove(0));
                        else
                            break;
                    }
                }
            };
            thread.start();
        }

        System.out.println("start2...");
        new Thread() {
            public void run() {
                for (String s : tickets) {
                    System.out.println(s);
                }
            }
        }.start();

(3)获取线程安全的集合
1.使用vector、stack、hashtable、enumeration等线程安全的集合类。
2.使用Collections.synchronizedxxx 将非线程安全的集合转换成线程安全的集合。
3.使用 jdk1.5之后新的线程安全集合类,如ConcurrentLinkedQueue、ConcurrentHashMap等。

2.使用注意事项

(1)ArrayList 等顺序存放集合适合随机访问,LinkList 等链表形式存放集合适合插入删除和迭代操作。
(2)Collection接口继承了Iterable接口,除 map 外每个集合都支持迭代遍历和 foreach 功能。
(3)WeakHashMap支持 key 回收,提升性能,在开源项目Android-Universal-Image-Loader 中用WeakHashMap保存需要显示的 ImageView 支持回收。
(4)HashMap 的 key 判断相同的标准是 key 的 equal 和 hashcode 相同。如下

private static void testHashMapKey() {
        System.out.println("------test hash map key start------");
        String[] sampleTest = { "Aa", "BB", "aa" };
        HashMap<StringEqual, Integer> strHaspMap = new HashMap<HashMapDemo.StringEqual, Integer>();
        StringEqual[] strArray = { new StringEqual(sampleTest[0]),
                new StringEqual(sampleTest[1]), new StringEqual(sampleTest[2]) };
        //key是否相同的判断是equal和hash都相同,Aa和BB的hash相同
        strHaspMap.put(strArray[0], 0);
        strHaspMap.put(strArray[1], 1);
        strHaspMap.put(strArray[2], 2);
        Set<StringEqual> set = strHaspMap.keySet();
        for (StringEqual str : set) {
            System.out.println(strHaspMap.get(str));
        }
    }

    private static class StringEqual {
        private String str;

        public StringEqual(String str) {
            this.str = str;
        }

        @Override
        public boolean equals(Object obj) {
            return true;
        }

        @Override
        public int hashCode() {
            return str.hashCode();
        }
    }
------test hash map key start------
1
2

String 的 hashcode 算法是s[0]*31^(n-1) + s[1]*31^(n-2) + … + s[n-1],”Aa”和”BB”的hash相同,StringEqual类的 equal 默认为 true,则”Aa”和”BB”认定为同一个 key。

版权声明:本文为博主原创文章,未经博主允许不得转载。

java-集合类(二)

标签:集合   java   

原文地址:http://blog.csdn.net/wangpeifeng669/article/details/47167779

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!