Spec-Zone.ru › OpenJDK 17

Класс CyclicBarrier

java.lang.Object
java.util.concurrent.CyclicBarrier
public class CyclicBarrier extends Object
Сynchronizatsionная утилита, позволяющая набору потоков ждать друг друга у общей точки барьера. CyclicBarriers полезны в программах с фиксированным количеством потоков, которые должны периодически ждать друг друга. Барьер называется циклическим, потому что его можно повторно использовать после освобождения ожидающих потоков.

CyclicBarrier поддерживает необязательную команду Runnable, которая выполняется один раз на каждую точку барьера после того, как последний поток в группе достигнет её, но перед тем как любые потоки будут освобождены. Это действие барьера полезно для обновления общего состояния перед продолжением работы потоков.

Пример использования: Вот пример использования барьера в параллельном декомпозиционном дизайне:

 
 class Solver {
   final int N;
   final float[][] data;
   final CyclicBarrier barrier;

   class Worker implements Runnable {
     int myRow;
     Worker(int row) { myRow = row; }
     public void run() {
       while (!done()) {
         processRow(myRow);

         try {
           barrier.await();
         } catch (InterruptedException ex) {
           return;
         } catch (BrokenBarrierException ex) {
           return;
         }
       }
     }
   }

   public Solver(float[][] matrix) {
     data = matrix;
     N = matrix.length;
     Runnable barrierAction = () -> mergeRows(...);
     barrier = new CyclicBarrier(N, barrierAction);

     List<Thread> threads = new ArrayList<>(N);
     for (int i = 0; i < N; i++) {
       Thread thread = new Thread(new Worker(i));
       threads.add(thread);
       thread.start();
     }

     // wait until done
     for (Thread thread : threads)
       try {
         thread.join();
       } catch (InterruptedException ex) { }
   }
 }
Здесь каждый рабочий поток обрабатывает строку матрицы, а затем ждёт у барьера, пока все строки не будут обработаны. Когда все строки обработаны, заданное действие Runnable барьера выполняется, и строки объединяются. Если объединение определит, что решение найдено, то done() вернёт true , и каждый рабочий поток завершится.

Если действие барьера не зависит от приостановки потоков при его выполнении, то любой из потоков в группе может выполнить это действие при освобождении. Для этого каждое вызов await() возвращает индекс прибытия этого потока у барьера. Вы можете выбрать, какой поток должен выполнить действие барьера, например:

 
 if (barrier.await() == 0) {
   // log the completion of this iteration
 }

Данный CyclicBarrier использует модель «все или ничего» для не удачных попыток синхронизации: если поток покидает точку барьера преждевременно из-за прерывания, ошибки или таймаута, все остальные потоки, ожидающие у этой точки барьера, также покинут его аномально посредством BrokenBarrierException (или InterruptedException, если они также были прерваны примерно в то же время).

Эффекты согласованности памяти: действия в потоке до вызова await() предшествуют действиям, которые являются частью действия барьера, а это в свою очередь предшествует действиям, следующим за успешным возвратом из соответствующего await() в других потоках.

Since:
1.5
See Also:
  • CountDownLatch
  • Phaser

Краткое описание конструкторов

Конструктор Описание
CyclicBarrier(int parties)
Создаёт новый CyclicBarrier , который срабатывает, когда заданное количество участников (потоков) ожидают его, и не выполняет предопределённое действие при срабатывании барьера.
CyclicBarrier(int parties, Runnable barrierAction)
Создаёт новый CyclicBarrier , который срабатывает, когда заданное количество участников (потоков) ожидают его, и который выполнит заданное действие барьера при срабатывании барьера, выполняемое последним входящим потоком.

Краткое описание методов

Модификатор и тип Метод Описание
int await()
Ожидает, пока все участники не вызовут await на этом барьере.
int await(long timeout, TimeUnit unit)
Ожидает, пока все участники не вызовут await на этом барьере, или заданное время ожидания истечёт.
int getNumberWaiting()
Возвращает количество участников, которые в настоящее время ожидают у барьера.
int getParties()
Возвращает количество участников, необходимых для срабатывания этого барьера.
boolean isBroken()
Определяет, находится ли этот барьер в состоянии разрыва.
void reset()
Сбрасывает барьер в его начальное состояние.

Методы, унаследованные от класса java.lang.Object

clone, equals, finalize, getClass, hashCode, notify, notifyAll, toString, wait, wait, wait

Подробное описание конструкторов

CyclicBarrier

public CyclicBarrier(int parties, Runnable barrierAction)
Создаёт новую CyclicBarrier, которая будет срабатывать, когда заданное количество участников (потоков) будут ожидать её, и которая выполнит заданное действие барьера, когда барьер будет срабатывать, выполненное последним потоком, входящим в барьер.
Параметры:
parties - количество потоков, которые должны вызвать await(), прежде чем барьер сработает
barrierAction - команда для выполнения, когда барьер срабатывает, или null если действия нет
Исключения:
IllegalArgumentException - если parties меньше 1

CyclicBarrier

public CyclicBarrier(int parties)
Создаёт новую CyclicBarrier, которая будет срабатывать, когда заданное количество участников (потоков) будут ожидать её, и не выполняет предварительно заданного действия, когда барьер срабатывает.
Параметры:
parties - количество потоков, которые должны вызвать await(), прежде чем барьер сработает
Исключения:
IllegalArgumentException - если parties меньше 1

Подробное описание методов

getParties

public int getParties()
Возвращает количество участников, необходимое для срабатывания этого барьера.
Возвращает:
количество участников, необходимых для срабатывания этого барьера

await

public int await() throws InterruptedException, BrokenBarrierException
Ожидает, пока все участники не вызовут await в этом барьере.

Если текущий поток не является последним, прибывшим, то он отключается для целей планирования потоков и остаётся неактивным, пока не произойдёт одно из следующих событий:

  • Приходит последний поток; или
  • Какой-то другой поток прерывает текущий поток; или
  • Какой-то другой поток прерывает один из других ожидающих потоков; или
  • Какой-то другой поток истекает время ожидания барьера; или
  • Какой-то другой поток вызывает reset() в этом барьере.

Если текущий поток:

  • имеет установленный флаг прерывания при входе в этот метод; или
  • прерывается во время ожидания
тогда InterruptedException выбрасывается, а флаг прерывания текущего потока сбрасывается.

Если барьер reset() в то время, когда какой-либо поток ожидает, или если барьер неработоспособен когда await вызывается, или в то время, когда какой-либо поток ожидает, то BrokenBarrierException выбрасывается.

Если какой-либо поток прерывается во время ожидания, тогда все остальные ожидающие потоки выбросят BrokenBarrierException, и барьер переведён в неработоспособное состояние.

Если текущий поток является последним прибывшим потоком, и в конструкторе был задан ненулевой барьерный экшен, тогда текущий поток выполняет экшен до того, как позволит другим потокам продолжить. Если во время выполнения барьерного экшена возникает исключение, то это исключение будет распространено в текущем потоке и барьер переведён в неработоспособное состояние.

Возвращает:
индекс прибытия текущего потока, где индекс getParties() - 1 обозначает первый прибывший, а ноль - последний прибывший
Исключения:
InterruptedException - если текущий поток был прерван во время ожидания
BrokenBarrierException - если другой поток был прерван или истекло время ожидания, пока текущий поток ожидал, или барьер был сброшен, или барьер был нарушен при вызове await, или действие барьера (если оно присутствует) завершилось с ошибкой

await

public int await(long timeout, TimeUnit unit) throws InterruptedException, BrokenBarrierException, TimeoutException
Ожидает, пока все участники не вызовут await в этом барьере или истечёт заданное время ожидания.

Если текущий поток не является последним, прибывшим, то он отключается для целей планирования потоков и остаётся неактивным, пока не произойдёт одно из следующих событий:

  • Приходит последний поток; или
  • Истекает заданное время ожидания; или
  • Какой-то другой поток прерывает текущий поток; или
  • Какой-то другой поток прерывает один из других ожидающих потоков; или
  • Какой-то другой поток истекает время ожидания барьера; или
  • Какой-то другой поток вызывает reset() в этом барьере.

Если текущий поток:

  • имеет установленный флаг прерывания при входе в этот метод; или
  • прерывается во время ожидания
тогда InterruptedException выбрасывается, а флаг прерывания текущего потока сбрасывается.

Если заданное время ожидания истекает, то TimeoutException выбрасывается. Если время меньше или равно нулю, метод не будет ожидать вообще.

Если барьер reset() в то время, когда какой-либо поток ожидает, или если барьер неработоспособен когда await вызывается, или в то время, когда какой-либо поток ожидает, то BrokenBarrierException выбрасывается.

Если какой-либо поток прерывается во время ожидания, тогда все остальные ожидающие потоки выбросят BrokenBarrierException, и барьер переведён в неработоспособное состояние.

Если текущий поток является последним прибывшим потоком, и в конструкторе был задан ненулевой барьерный экшен, тогда текущий поток выполняет экшен до того, как позволит другим потокам продолжить. Если во время выполнения барьерного экшена возникает исключение, то это исключение будет распространено в текущем потоке и барьер переведён в неработоспособное состояние.

Параметры:
timeout - время ожидания барьера
unit - единица измерения времени параметра timeout
Возвращает:
индекс прибытия текущего потока, где индекс getParties() - 1 обозначает первый прибывший, а ноль - последний прибывший
Исключения:
InterruptedException - если текущий поток был прерван во время ожидания
TimeoutException - если заданное время ожидания истекает. В этом случае барьер будет нарушен.
BrokenBarrierException - если другой поток был прерван или истекло время ожидания, пока текущий поток ожидал, или барьер был сброшен, или барьер был нарушен при вызове await, или действие барьера (если оно присутствует) завершилось с ошибкой

isBroken

public boolean isBroken()
Определяет, находится ли этот барьер в состоянии нарушения.
Возвращает:
true если один или несколько участников нарушили этот барьер из-за прерывания или истечения времени ожидания с момента создания или последнего сброса, или действие барьера завершилось с ошибкой; false в противном случае.

reset

public void reset()
Сбрасывает барьер в начальное состояние. Если какие-либо участники в настоящее время ожидают в барьере, они вернутся с BrokenBarrierException. Обратите внимание, что сбросы после того, как произошёл сбой по другим причинам, могут быть сложными для выполнения; потоки должны повторно синхронизироваться каким-то другим способом, и выбрать один для выполнения сброса. Может быть предпочтительнее создать новый барьер для последующего использования.

getNumberWaiting

public int getNumberWaiting()
Возвращает количество участников, которые в настоящее время ожидают в барьере. Этот метод в первую очередь полезен для отладки и утверждений.
Возвращает:
количество участников, которые в настоящее время заблокированы в await()

© 1993, 2021, Oracle and/or its affiliates. All rights reserved.
Documentation extracted from Debian's OpenJDK Development Kit package.
Licensed under the GNU General Public License, version 2, with the Classpath Exception.
Various third party code in OpenJDK is licensed under different licenses (see Debian package).
Java and OpenJDK are trademarks or registered trademarks of Oracle and/or its affiliates.
https://docs.oracle.com/en/java/javase/17/docs/api/java.base/java/util/concurrent/CyclicBarrier.html

Spec-Zone.ru

Настройки Оффлайн Что нового Помощь О нас
Spec-Zone .ru
спецификации, руководства, описания, API