首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >简单说明 lock 锁和 Condition 的操作

简单说明 lock 锁和 Condition 的操作

作者头像
潇洒
发布2019-07-02 18:05:33
8310
发布2019-07-02 18:05:33
举报
文章被收录于专栏:石头岛石头岛

作用:使当前线程进入等待状,并交换执行执,等待被交换的当前执行线程唤醒,才可以继续执行,如果不被唤醒? 场景:多个线程操作同一个共享资源时使用。

Condition 是执行条件。类似传统技术中的 wait 的 notify 功能。 Condition 是基于一个 lock 而存在。 注意的是,Condition 的创建来自同一个 lock 对象,

Condition 也行 wait 也好,套路就是使用三个工具来完成三步套路。即,用两个线程,同时跑两个代码,并且用 while 不段的去读取一个条件,来判断自己是否应该唤醒对方。

步骤: 1.先lock住 2.通过 lock 拿到 condition。再进行操作如 await 3.然后多个线程开始 await、single 注意 await 会释放锁。

await()的作用是能够让其他线程访问竞争资源,所以挂起状态就是要释放竞争资源的锁。
package com.liukai.thread.lock.condition;

import java.util.concurrent.locks.Condition;
import java.util.concurrent.locks.Lock;
import java.util.concurrent.locks.ReentrantLock;

/**
 * Created by liukai on 2016/2/25.
 * 测试 Lock、Condition 代替 synchronized、wait
 * 例子来自 JDK Condition API 中的示例代码,阻塞队列的原理。
 * 注间的是,两个不同的方法里面的 等待 和 唤醒 是不同的对象
 */
public class TestCondition {

    private final Lock lock = new ReentrantLock();
    private final Condition full = lock.newCondition();
    private final Condition notFull = lock.newCondition();
    private int count = 0;
    private int takeptr = 0;
    private int putptr = 0;
    Object [] blockArray = new Object[100];

    public static void main(String[] args) {
        final TestCondition condition = new TestCondition();
        for (int i = 0; i < 100; i++) {
            new Thread(()->{
                try {
                    condition.put(new Object());
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
            }).start();

            new Thread(()->{
                try {
                    condition.take();
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
            }).start();

        }
    }

    public void put (Object element) throws InterruptedException {
        try {
            lock.lock();
            while (count == blockArray.length) {
                System.out.println("put: putptr = " + putptr + ", await");
                full.await();       //等待和唤醒用的不是同一个对象
            }
            System.out.println("put: putptr = " + putptr + ", 执行 put");
            blockArray[putptr] = element;
            if (++putptr == blockArray.length) {
                putptr = 0;
            }
            ++count;
            notFull.signal();
        } finally {
            lock.unlock();
        }
    }

    public Object take() throws InterruptedException {
        lock.lock();
        Object data = null;
        try {
            while (0 == count) {
                System.out.println("take: takeptr == " + takeptr + ",await");
                notFull.await();
            }
            System.out.println("take: takeptr = " + takeptr + ", 执行 take");
            data = blockArray[takeptr];
            if (++takeptr == blockArray.length) {
                takeptr = 0;
            }
            --count;
            full.signal();
            return data;
        } finally {
            lock.unlock();
        }
    }
}
本文参与 腾讯云自媒体分享计划,分享自作者个人站点/博客。
原始发表:2016-08-09,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体分享计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档