[转载]关于 java.util.concurrent 您不知道的 5 件事

    技术2022-05-18  17

    关于 java.util.concurrent 您不知道的 5 件事 

    http://www.ibm.com/developerworks/cn/java/j-5things4.html

    http://www.ibm.com/developerworks/cn/java/j-5things5.html

     

    1 TimeUnit

    2 CopyOnWriteArrayList

        在CopyOnWriteArrayList 中含有一个数组:

        /** The array, accessed only via getArray/setArray. */    private volatile transient Object[] array;

     

        可以看出,volatile 修饰,所以可以线程安全的赋值(即在一个线程中赋值,另一个线程立刻可以发现这个赋值)。

        Iterator 在这个数组上迭代

        所有的变化的操作(如 add, set 等等),都运行在同步的情况下,如:

        /** * Appends the specified element to the end of this list. * * @param e element to be appended to this list * @return <tt>true</tt> (as specified by {@link Collection#add}) */ public boolean add(E e) { final ReentrantLock lock = this.lock; lock.lock(); try { Object[] elements = getArray(); int len = elements.length; Object[] newElements = Arrays.copyOf(elements, len + 1); newElements[len] = e; setArray(newElements); return true; } finally { lock.unlock(); } }

     

        可见修改时,copy 一个新的数组,在赋值回去。

        应用情况:遍历次数远大于变化操作。

        本质上讲,CopyOnWriteArrayList 很适合处理 ArrayList 经常让我们失败的这种场景:读取频繁,但很少有写操作的集合,例如 JavaBean 事件的 Listeners。

     

        注意:当A 线程通过Iterator 对CopyOnWriteArrayList 迭代中,B 线程修改这个CopyOnWriteArrayList,则B 线程的修改A 线程是看不到的。且Iterator 不支持remove, set, and add 的操作,如果调用则报UnsupportedOperationException。

     

        很奇怪,我认为应该可以看到啊?

        答案: 确实看不到,因为Iterator  中保存的是旧的数组,一旦CopyOnWriteArrayList  有修改操作,会立即重新创建一个新的数组。(这个新的数组和Iterator  中的旧数组不是一个对象了)

     

        测试程序:

    /** * @author alf */ public class TestCopyOnWriteArrayList { @SuppressWarnings("unchecked") public static void main(String[] args) throws InterruptedException { final CopyOnWriteArrayList copyOnWriteArrayList = new CopyOnWriteArrayList(); copyOnWriteArrayList.add("11111"); copyOnWriteArrayList.add("22222"); copyOnWriteArrayList.add("33333"); copyOnWriteArrayList.add("44444"); copyOnWriteArrayList.add("55555"); Thread thread = new Thread(){ @Override public void run() { copyOnWriteArrayList.add("BBB"); copyOnWriteArrayList.set(4, "haha"); System.out.println("--------------"); } }; int i = 0; Iterator it = copyOnWriteArrayList.iterator(); while (it.hasNext()) { i++; if (i== 3) { thread.start(); thread.join(); } System.out.println(it.next()); } } }

        测试结果为:

              11111          22222           --------------          33333          44444          55555

     

    3 BlockingQueue

    4 ConcurrentMap

    5 SynchronousQueues

    6 Semaphore

    7 CountDownLatch

    8 Executor

    9 ExecutorService

    10 ScheduledExecutorServices

    11 Timeout 方法


    最新回复(0)