1. 程式人生 > >重入鎖--ReentrantLock

重入鎖--ReentrantLock

public class FairAndUnfairTest {
    private static Lock fairLock = new ReentrantLock2(true);
    private static Lock unfairLock = new ReentrantLock2(false);
    @Test
    public void fair() throws Exception {
        System.out.println("公平鎖");
        testLock(fairLock);
    }
    @Test
    public void unfair() throws Exception {
        System.out.println("非公平鎖");
        testLock(unfairLock);
    }
    public void testLock(Lock lock) throws Exception {
        new Thread(new Runnable() {
            @Override
            public void run() {
                for(int i=1; i<6; i++){
                    Thread thread = new Job(lock);
                    thread.setName(""+i+"");
                    thread.start();
                    mySleep(500);
                }
            }
        }).start();
        Thread.sleep(500);
        new Thread(new Runnable() {
            @Override
            public void run() {
                for(int i=6; i<11; i++){
                    Thread thread = new Job(lock);
                    thread.setName(""+i+"");
                    thread.start();
                    mySleep(500);
                }
            }
        }).start();

        Thread.sleep(11000);
    }

    private static class Job extends Thread{
        private Lock lock;
        public Job(Lock lock){
            this.lock = lock;
        }

        public void run(){
            for(int i=0; i<2; i++){
                lock.lock();
                try {
                    Thread.sleep(500);
                    System.out.println("lock by [" + Thread.currentThread().getName() + "], waiting by " + ((ReentrantLock2)lock).getQueuedThread());
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
                lock.unlock();
                try {
                    Thread.sleep(100);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
            }
        }
    }

    public static class ReentrantLock2 extends ReentrantLock{
        public ReentrantLock2(boolean fair){
            super(fair);
        }

        public Collection<String> getQueuedThread(){
            List<Thread> arrayList = new ArrayList<Thread>(super.getQueuedThreads());
            Collections.reverse(arrayList);
            List<String> list = new ArrayList<>();
            for(Thread thread:arrayList){
                list.add(thread.getName());
            }
            return list;
        }
    }

    private void mySleep(int time){
        try {
            Thread.sleep(time);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
    }
}