Page 256 - 6253
P. 256

тобто стати меншим дозволеної межі. Тому необхідно певним чином гарантувати,

            що жодний інший потік не зможе змінити залишок на рахунку між його перевіркою

            і переказом коштів. Для цього потрібно захистити як перевірку залишку на рахунку,

            так і сам переказ коштів, що можна зробити за допомогою наступного рішення:

                  public void transfer(int from, int to, int amount) {
                     bankLock.lock();
                     try {

                        while (accounts[from] < amount) {
                           // очікувати

                        }
                        // перевести кошти
                     } finally {

                        bankLock.unlock();
                     }
                  }

                  Проте, що робити, якщо на рахунку немає достатньої кількості коштів? Єдине

            рішення  –  це  очікувати  до  того  часу,  поки  рахунок  не  буде  поповнено  під  час

            виконання  іншого  потоку.  Проте,  у  представленому  прикладі  потік  володіє

            монопольним  доступом  до  об’єкта  bankLock,  тому  жоден  інший  потік  не  в  змозі

            виконати поповнення рахунку. Тому єдиним правильним рішенням є використання

            умовного об’єкту.

                  З  будь-яким  об’єктом  блокування  може  бути  пов’язаний  один  або  декілька

            умовних  об’єктів,  які  створюються  за  допомогою  фабричного  методу

            newCondition().  Кожному  умовному  об’єкту  можна  присвоїти  ім’я,  що  буде

            асоціюватися  з  умовою,  яку  він  представляє.  Наприклад,  об’єкт,  що  представляє

            умову «достатньо коштів», визначається наступним чином:

                  class Bank {
                     private Condition sufficientFunds;

                     ...
                     public Bank() {
                        ...

                        sufficientFunds = bankLock.newCondition();
                     }

                  }
                  Фабричний  метод  newCondition()  повертає  умовний  об’єкт,  пов’язаний  з




                                                              255
   251   252   253   254   255   256   257   258   259   260   261