CodeGym/Java курс/Модул 3/Синхронизатори: Синхронизиране на достъпа до ресурси в Ja...

Синхронизатори: Синхронизиране на достъпа до ресурси в Java

На разположение

Семафор

Семафорите обикновено се използват, когато е необходимо да се ограничи броят на нишките при работа с файловата система. Достъпът до файл or друг споделен ресурс се контролира чрез брояч. Ако стойността му е по-голяма от нула, достъпът е разрешен, но в същото време броячът ще намалява.

В момента, когато броячът върне нула, текущата нишка ще бъде блокирана, докато ресурсът не бъде освободен от друга нишка. Параметърът брой разрешения трябва да бъде зададен чрез конструктора.

Трябва да изберете този параметър индивидуално, в зависимост от мощността на вашия компютър or лаптоп.

public class Main {

   public static void main(String[] args) {
       Semaphore sem = new Semaphore(1);
       CommonResource res = new CommonResource();
       new Thread(new MyThread(res, sem, "MyThread_1")).start();
       new Thread(new MyThread(res, sem, "MyThread_2")).start();
       new Thread(new MyThread(res, sem, "MyThread_3")).start();
   }
}

class CommonResource {
   int value = 0;
}

class MyThread implements Runnable {
   CommonResource commonResource;
   Semaphore semaphore;
   String name;
   MyThread(CommonResource commonResource, Semaphore sem, String name) {
       this.commonResource = commonResource;
       this.semaphore = sem;
       this.name = name;
   }

   public void run() {

       try {
           System.out.println(name + "waiting permission");
           semaphore.acquire();
           commonResource.value = 1;
           for (int i = 1; i < 7; i++) {
               System.out.println(this.name + ": " + commonResource.value);
               commonResource.value++;
               Thread.sleep(150);
           }
       } catch (InterruptedException e) {
           System.out.println(e.getMessage() + " " + name);
           Thread.currentThread().interrupt();
       }
       System.out.println(name + "releases permission");
       semaphore.release();
   }
}

CountDownLatch и други

CountDownLatch - Позволява на множество нишки да изчакат, докато не завършат определен брой операции, извършени върху други нишки. Пример е инсталирането на приложение: то няма да стартира, докато не приемете условията за ползване, докато не изберете папка, в която да инсталирате нова програма и т.н. За това има специален метод countDown() - този метод намалява брояча за обратно броене с единица.

Веднага след като броячът достигне нула, всички чакащи нишки в await ще продължат работата си и всички следващи извиквания на await ще преминат без изчакване. Броячът за обратно броене е еднократен и не може да се нулира.

CyclicBarrier - използва се за синхронизиране на даден брой нишки в една точка. Бариерата се достига, когато N нишки извикат метода await(...) и блокират. След това броячът се нулира до първоначалната си стойност и чакащите нишки ще бъдат освободени. Освен това, ако е необходимо, е възможно да стартирате персонализиран code, преди да деблокирате нишки и да нулирате брояча. За да направите това, обект с имплементация на интерфейса Runnable се предава през конструктора .

Exchanger<V> класът Exchanger е предназначен за обмен на данни между нишки. Той се въвежда и въвежда типа данни, които нишките трябва да обменят.

Данните се обменят с помощта на единствения метод exchange() от този клас :

V exchange(V x) throws InterruptedException
V exchange(V x, long timeout, TimeUnit unit) throws InterruptedException, TimeoutException

Параметърът x представлява буфера за данни, който трябва да се обменя. Втората форма на метода също дефинира параметъра за изчакване , времето за изчакване и единица , типа единица за време, която да се използва за параметъра за изчакване .

Класът Phaser ви позволява да синхронизирате нишки, които представляват една фаза or етап в изпълнението на цялостно действие. Phaser дефинира обект за синхронизация, който изчаква завършването на определена фаза. След това Phaser преминава към следващия етап or фаза и изчаква да завърши отново.

Когато работите с клас Phaser , обичайно е първо да създадете неговия обект. След това трябва да регистрираме всички участници. За да се регистрирате за всеки участник, се извиква методът register() or можете да го направите без този метод, като подадете необходимия брой участници на конструктора на Phaser .

След това всеки участник изпълнява определен набор от действия, които съставят фазата. И синхронизаторът Phaser изчаква, докато всички участници завършат изпълнението на фазата. За да информира синхронизатора, че фазата е приключила, участникът трябва да извика метода arrive() or earnAndAwaitAdvance() . След това синхронизаторът преминава към следващата фаза.

1
Задача
Модул 3,  нивоурок
Заключено
Arbeiten!
task4207
Коментари
  • Популярен
  • Нов
  • Стар
Трябва да сте влезли, за да оставите коментар
Тази страница все още няма коментари