当程序中使用Lock(),unLock()作为线程通信的方式时,就不存在隐式的同步监视器,不能够使用wait()、notify()、notifyAll()进行线程通信了。Condition与Lock对象绑定,通过Lock对象的newCondition方法获得,可以让已经得到Lock对象却无法执行的线程释放Lock对象,也可以唤醒其它处于等待的线程。

public class Account {
    private final Lock lock = new ReentrantLock();
    private final Condition cond = lock.newCondition();
    private String accountNo;
    private double balance;
    private boolean flag = false;

    public Account() {
    }

    public Account(String accounNo, double balance) {
        this.accountNo = accounNo;
        this.balance = balance;
    }

    public double getBalance() {
        return this.balance;
    }

    public void draw(double drawAmount) {
        lock.lock();
        try {
            if (!flag) {

                cond.await();
            } else {
                System.out.println(Thread.currentThread().getName() + " draw "
                        + drawAmount);
                balance -= drawAmount;
                System.out.println("current balance is" + balance);
                flag = false;
                cond.signalAll();
            }
        } catch (InterruptedException e) {
            e.printStackTrace();
        } finally {
            lock.unlock();
        }

    }

    public void deposit(double depositAmount) {
        lock.lock();
        try {
            if (flag) {
                cond.await();
            } else {
                balance += depositAmount;
                System.out.println(Thread.currentThread().getName()
                        + "deposit " + depositAmount);
                flag = true;
                cond.signalAll();
            }
        } catch (InterruptedException e) {
            e.printStackTrace();
        } finally {
            lock.unlock();
        }
    }

    @Override
    public int hashCode() {
        final int prime = 31;
        int result = 1;
        result = prime * result
                + ((accountNo == null) ? 0 : accountNo.hashCode());
        return result;
    }

    @Override
    public boolean equals(Object obj) {
        if (this == obj)
            return true;
        if (obj == null)
            return false;
        if (getClass() != obj.getClass())
            return false;
        Account other = (Account) obj;
        if (accountNo == null) {
            if (other.accountNo != null)
                return false;
        } else if (!accountNo.equals(other.accountNo))
            return false;
        return true;
    }
}