zoukankan      html  css  js  c++  java
  • 多线程的Lock锁——ReentrantReadWriteLock

            上一篇讲到ReentrantLock是排他性,一方面保证了线程的绝对安全,但另一方面降低了效率。对于一些不需要操作实例变量的方法中,有另外一种锁可以提高运行效率,这种锁就是ReadWriteReentrantLock。

            ReentrantReadWriteLock,也称为读写锁。读写锁有两个锁,一个是读操作相关的锁,也叫共享锁;另一个是写操作相关锁,也叫排他锁

            读锁之间不互斥,写锁之间互斥,读写锁之间互斥。

    使用

    private ReadWriteLock lock = new ReentrantReadWriteLock();
    
    lock.readLock().lock();
    .
    .
    .
    lock.readLock().unlock();
    
    lock.writeLock().lock();
    .
    .
    .
    lock.writeLock().unlock();

    举个具体例子:

    1、创建服务类

    package com.cjs.ReadWriteLock_3;
     
    import java.util.concurrent.locks.ReadWriteLock;
    import java.util.concurrent.locks.ReentrantReadWriteLock;
     
    public class Service {
        private ReadWriteLock lock = new ReentrantReadWriteLock();
     
        public void read() {
            try {
                try {
                    lock.readLock().lock();
                    System.out.println("获得读锁:" + Thread.currentThread().getName() + " " + System.currentTimeMillis());
                    Thread.sleep(3000);
                } finally {
                    lock.readLock().unlock();
                }
            } catch (Exception e) {
                e.printStackTrace();
            }
        }
     
        public void write() {
            try {
                try {
                    lock.writeLock().lock();
                    System.out.println("获得写锁:" + Thread.currentThread().getName() + " " + System.currentTimeMillis());
                    Thread.sleep(3000);
                } finally {
                    lock.writeLock().unlock();
                }
            } catch (Exception e) {
                e.printStackTrace();
            }
        }
    }

    2、创建两个线程类,

    package com.cjs.ReadWriteLock_3;
     
    public class ReadThread extends Thread {
        private Service service;
     
        @Override
        public void run() {
            service.read();
        }
     
        public ReadThread(Service service) {
            this.service = service;
        }
    }
    package com.cjs.ReadWriteLock_3;
     
    public class WriteThread extends Thread {
        private Service service;
     
        public WriteThread(Service service) {
            this.service = service;
        }
     
        @Override
        public void run() {
            service.write();
        }
    }

    3、创建一个Main类,

    package com.cjs.ReadWriteLock_3;
     
    public class Run {
        public static void main(String[] args) {
            Service service = new Service();
            ReadThread[] readThreads = new ReadThread[10];
            WriteThread[] writeThreads = new WriteThread[10];
            for (int i = 0; i < 10; i++) {
                readThreads[i] = new ReadThread(service);
                readThreads[i].setName("ReadThread" + (i + 1));
                readThreads[i].start();
                writeThreads[i] = new WriteThread(service);
                writeThreads[i].setName("WriteThread" + (i + 1));
                writeThreads[i].start();
            }
        }
    }

    4、运行程序,

     

     注意框框的两条记录,上面提及的读写锁之间的两两特性,只有当当前持有写锁时,其他线程才会进入阻塞状态,如果是持有读锁,那么还是会有可能另一个线程获得读锁。

     

  • 相关阅读:
    中国省市区县最新数据表
    Android基础之退出键及menu不能使用
    对Hello China操作系统比较客观的评价
    对操作系统开发相关的一些问题的思考
    2010年9月12日周日_Builing your first mobile application_1.3
    2010年9月13日周一_WorkingWithSpatialReferences_6.2
    2010年9月04日_周六_Mobile Developmnet Environmnet_1
    2010年9月05日_周日_DeveloperEnvironmentRequirements_1.1
    2010年9月02日周四_Deploying to Mobile Devices_4.2
    2010年9月16日周四_Working with geometry_6.3
  • 原文地址:https://www.cnblogs.com/SysoCjs/p/10319520.html
Copyright © 2011-2022 走看看