import java.util.concurrent.locks.*;

public class BankAccountRW{
    double balance = 0.0;
    int readers = 0;
    boolean writing = false;
    ReentrantLock mutex = new ReentrantLock();
    Condition waitWriting = mutex.newCondition();
    Condition waitReading = mutex.newCondition();

    public void deposit(double amount) throws InterruptedException{
	mutex.lock();
        while (readers > 0|| writing) waitWriting.await();
        try{
	    writing = true;
            balance = balance+amount;
            save();
            writing = false;
            if (mutex.getWaitQueueLength(waitReading)>0) 
                 waitReading.signalAll();
            else
		waitWriting.signal();
	}
	finally{
	    mutex.unlock();
	}
    }
    public void withdraw(double amount)throws InterruptedException{
	mutex.lock();
        while (readers > 0|| writing) waitWriting.await();
        try{
          writing = true;
          balance = balance-amount;
          save();
          writing = false;
          if (mutex.getWaitQueueLength(waitReading)>0) 
                waitReading.signalAll();
          else
		waitWriting.signal();
	}
	finally{
	    mutex.unlock();
	}
    }
    public double getBalance()throws InterruptedException{
     	mutex.lock();
        try{
            while (writing ||
                  (mutex.getWaitQueueLength(waitWriting)>0)) 
		waitReading.await();
			      readers++;
	    return balance;
	}
	finally{
	    readers--;
	     if (readers == 0) waitWriting.signal();
	     mutex.unlock();
	}
    }
    public void save(){}

}
