Интерфейс StructuredTaskScope<T, R>
- Параметры типа:
T— тип результата подзадач, выполняемых в областиR— тип результата области
- Все суперинтерфейсы:
AutoCloseable
public sealed interface StructuredTaskScope<T,R> extends AutoCloseable
StructuredTaskScope — предварительная версия API платформы Java. StructuredTaskScope поддерживает случаи, когда выполнение задачи (единицы работы) разделяется на несколько конкурентных подзадач, которые должны завершиться до продолжения задачи.
StructuredTaskScope можно использовать, чтобы гарантировать, что время жизни конкурентной операции ограничено блоком кода, подобно последовательной операции в структурном программировании. StructuredTaskScope определяет статический метод open для открытия новой StructuredTaskScope и метод close для её закрытия. API предназначен для использования с оператором try-with-resources, в котором StructuredTaskScope открывается как ресурс, а затем закрывается автоматически. Код внутри блока использует метод fork для запуска подзадач. После запуска подзадач он использует метод join, чтобы дождаться завершения всех подзадач (или иного исхода) как одной операции. Запуск подзадачи создаёт новый Thread для её выполнения. Поток, выполняющий задачу, не продолжит выполнение за пределами метода close, пока не завершатся все потоки, запущенные для выполнения подзадач. Для обеспечения корректного использования методы fork, join и close могут вызываться только владеющим потоком (потоком, открывшим
StructuredTaskScope), метод fork нельзя вызывать после join, метод join можно вызвать только один раз, а метод close после закрытия выбрасывает исключение, если владеющий поток не вызвал метод join после запуска подзадач.
В качестве первого примера рассмотрим задачу, которая разделяется на две подзадачи для одновременного получения ресурсов из двух URL-адресов — «left» и «right». Обе подзадачи могут завершиться успешно, одна подзадача может завершиться успешно, а другая — неудачно, или обе подзадачи могут завершиться неудачно. В этом примере задаче нужны успешные результаты обеих подзадач. Метод join ожидает успешного завершения обеих подзадач или сбоя любой из них.
try (var scope = StructuredTaskScope.open()) {
Subtask<String> subtask1 = scope.fork(() -> query(left));
Subtask<Integer> subtask2 = scope.fork(() -> query(right));
// throws if either subtask fails
scope.join();
// both subtasks completed successfully
return new MyResult(subtask1.get(), subtask2.get());
} // close
Если обе подзадачи завершаются успешно, метод join завершается нормально, и задача использует метод Subtask.get()ПРЕДВАРИТЕЛЬНАЯ ВЕРСИЯ, чтобы получить результат каждой подзадачи. Если одна из подзадач завершается неудачно, другая подзадача отменяется (это приведёт к прерыванию потока, выполняющего другую подзадачу), а метод join выбрасывает StructuredTaskScope.FailedExceptionПРЕДВАРИТЕЛЬНАЯ ВЕРСИЯ, указав исключение сбойной подзадачи в качестве причины.
Чтобы обеспечить отмену, подзадачи должны быть написаны так, чтобы они завершались как можно скорее после прерывания. Подзадачи, не реагирующие на прерывание, например блокирующиеся при вызове методов, не поддерживающих прерывание, могут бесконечно задерживать закрытие области. Метод close всегда ожидает завершения потоков, выполняющих подзадачи, даже если область отменена, поэтому выполнение не может продолжиться за пределами метода close, пока прерванные потоки не завершатся.
В этом примере подзадачи создают результаты разных типов (String и Integer). В других случаях все подзадачи могут создавать результаты одного типа. Если бы в примере использовался StructuredTaskScope.<String>open(), его можно было бы использовать только для запуска подзадач, возвращающих результат типа String.
Объединители
В приведённом выше примере задача завершается неудачно, если сбой происходит в любой подзадаче. Если все подзадачи завершаются успешно, метод join завершается нормально. Другие политики и исходы поддерживаются с помощью создания StructuredTaskScope с объектом StructuredTaskScope.JoinerПРЕДВАРИТЕЛЬНАЯ ВЕРСИЯ, реализующим нужную политику. Joiner обрабатывает завершение подзадач и формирует исход для метода join. В приведённом выше примере join возвращает null. В зависимости от Joiner, join может возвращать результат, поток элементов или другой объект. Интерфейс Joiner определяет фабричные методы для создания Joiner в некоторых распространённых случаях.
Joiner может отменить область (иногда это называют «прерыванием по условию»), когда достигается условие, при котором результат ещё выполняющихся подзадач не требуется. Отмена области предотвращает запуск новых потоков для выполнения последующих подзадач, прерывает потоки, выполняющие незавершённые подзадачи, и вызывает пробуждение метода join с результатом (значением или исключением). В приведённом выше примере исходом является завершение join с результатом null, когда все подзадачи завершаются успешно. Область отменяется, если любая из подзадач завершается неудачно, а join выбрасывает
FailedException, указав исключение сбойной подзадачи в качестве причины. Другие реализации
Joiner могут отменять область по другим причинам.
Рассмотрим другой пример, в котором задача разделяется на две подзадачи. В этом примере каждая подзадача создаёт результат типа String, и задаче нужен только результат первой успешно завершившейся подзадачи. В примере используется Joiner.anySuccessfulResultOrThrow()ПРЕДВАРИТЕЛЬНАЯ ВЕРСИЯ для создания Joiner, предоставляющего результат первой успешно завершившейся подзадачи. Параметр типа в примере — «String», поэтому можно запускать только подзадачи, возвращающие String.
try (var scope = StructuredTaskScope.open(Joiner.<String>anySuccessfulResultOrThrow())) {
scope.fork(callable1);
scope.fork(callable2);
// throws if both subtasks fail
String firstResult = scope.join();
}
В примере задача запускает две подзадачи, а затем ожидает в методе
join успешного завершения любой из них или сбоя обеих. Если одна из подзадач завершается успешно, Joiner вызывает отмену другой подзадачи (это прерывает поток, выполняющий её), а метод join возвращает результат успешно завершившейся подзадачи. Отмена другой подзадачи избавляет задачу от ожидания результата, который ей не нужен. Если обе подзадачи завершаются неудачно, метод join выбрасывает FailedException, указав исключение одной из подзадач в качестве причины.
Использовать ли кодом значение Subtask, возвращённое из fork, зависит от Joiner и сценария использования. Некоторые реализации Joiner подходят для подзадач, возвращающих результаты одного типа, и случаев, когда метод join возвращает результат, используемый задачей. Код, запускающий подзадачи с результатами разных типов и использующий Joiner, например Joiner.awaitAllSuccessfulOrThrow(), который не возвращает результат, после объединения использует Subtask.get()ПРЕДВАРИТЕЛЬНАЯ ВЕРСИЯ.
Обработка исключений
StructuredTaskScope открывается с объектом JoinerПРЕДВАРИТЕЛЬНАЯ ВЕРСИЯ, который обрабатывает завершение подзадач и формирует исход для метода join. В некоторых случаях исходом будет результат, в других — исключение. Если исходом является исключение, метод join выбрасывает StructuredTaskScope.FailedExceptionПРЕДВАРИТЕЛЬНАЯ ВЕРСИЯ, указав исключение в качестве причины. Во многих реализациях Joiner это будет исключение, выброшенное сбойной подзадачей. Например, в случае allSuccessfulOrThrowПРЕДВАРИТЕЛЬНАЯ ВЕРСИЯ и awaitAllSuccessfulOrThrowПРЕДВАРИТЕЛЬНАЯ ВЕРСИЯ исключение выбрасывает первая подзадача, завершившаяся неудачно.
Многие детали обработки исключений зависят от сценария использования. В некоторых случаях полезно добавить блок catch в оператор try-with-resources, чтобы перехватывать FailedException. Для обработки определённых причин в обработке исключений может использоваться
instanceof с сопоставлением с образцом.
try (var scope = StructuredTaskScope.open()) {
..
} catch (StructuredTaskScope.FailedException e) {
Throwable cause = e.getCause();
switch (cause) {
case IOException ioe -> ..
default -> ..
}
}
FailedException может быть нецелесообразен: вместо этого исключение можно передать настроенному обработчику неперехваченных исключений для регистрации. Если конкретное исключение приводит к использованию значения по умолчанию, уместнее обработать его в самой подзадаче, а не допускать сбой подзадачи и обработку исключения владельцем области.
Конфигурация
StructuredTaskScope открывается с конфигурацией, состоящей из ThreadFactory для создания потоков, необязательного имени для мониторинга и управления, а также необязательного времени ожидания. Методы open() и open(Joiner) создают StructuredTaskScope с конфигурацией по умолчанию. Конфигурация по умолчанию содержит ThreadFactory, создающий безымянные виртуальные потоки; сама конфигурация не имеет имени для мониторинга и управления и не задаёт время ожидания.
Метод open с двумя аргументами можно использовать для создания StructuredTaskScope, который использует другой ThreadFactory, имеет имя для мониторинга и управления или задаёт время ожидания, отменяющее область, если срок истекает до ожидания завершения подзадач или во время него. Метод open вызывается с функцией, которая применяется к конфигурации по умолчанию и возвращает ConfigurationПРЕДВАРИТЕЛЬНАЯ ВЕРСИЯ для создаваемой StructuredTaskScope.
В следующем примере открывается новая StructuredTaskScope с
ThreadFactory, создающим виртуальные потоки с именами «duke-0», «duke-1» и т. д.
ThreadFactory factory = Thread.ofVirtual().name("duke-", 0).factory();
try (var scope = StructuredTaskScope.open(joiner, cf -> cf.withThreadFactory(factory))) {
scope.fork( .. ); // runs in a virtual thread with name "duke-0"
scope.fork( .. ); // runs in a virtual thread with name "duke-1"
scope.join();
}
Во втором примере задаётся время ожидания, представленное объектом Duration. Отсчёт времени ожидания начинается при открытии новой области. Если срок истекает до завершения метода join, область отменяется. Это прерывает потоки, выполняющие две подзадачи, и приводит к тому, что метод join выбрасывает StructuredTaskScope.TimeoutExceptionПРЕДВАРИТЕЛЬНАЯ ВЕРСИЯ.
Duration timeout = Duration.ofSeconds(10);
try (var scope = StructuredTaskScope.open(Joiner.<String>allSuccessfulOrThrow(),
cf -> cf.withTimeout(timeout))) {
scope.fork(callable1);
scope.fork(callable2);
List<String> result = scope.join()
.map(Subtask::get)
.toList();
}
Наследование привязок значений области видимости
ScopedValue поддерживает выполнение метода, в котором ScopedValue привязано к значению на ограниченный период выполнения метода текущим потоком. Это позволяет безопасно и эффективно передавать значение методам без использования параметров метода. При совместном использовании с StructuredTaskScope, ScopedValue также может безопасно и эффективно передавать значение методам, выполняемым подзадачами, запущенными в области. Когда объект ScopedValue привязан к значению в потоке, выполняющем задачу, эта привязка наследуется потоками, созданными для выполнения подзадач. Поток, выполняющий задачу, не продолжит выполнение за пределами метода close, пока не завершатся все потоки, выполняющие подзадачи. Это гарантирует, что ScopedValue не станет непривязанным (или не вернётся к предыдущему значению), пока выполняются подзадачи. Помимо безопасного и эффективного способа наследования значения подзадачами, это наследование позволяет переработать последовательный код, использующий ScopedValue, и перейти к структурированной конкурентности.
Для обеспечения корректности при открытии новой StructuredTaskScope фиксируются привязки значений области видимости текущего потока. Именно эти привязки наследуются потоками, созданными для выполнения подзадач в области. При запуске подзадачи проверяется, совпадают ли действующие в этот момент привязки с привязками на момент создания StructuredTaskScope. Эта проверка гарантирует, что подзадача не унаследует привязку, которая будет отменена в задаче до завершения подзадачи.
Для совместного использования ScopedValue между потоками необходимо, чтобы значение было неизменяемым объектом или чтобы весь доступ к нему надлежащим образом синхронизировался.
В следующем примере демонстрируется наследование привязок значений области видимости. Значение области видимости USERNAME привязано к значению «duke» на ограниченный период выполнения лямбда-выражения потоком, который его выполняет. Код внутри блока открывает
StructuredTaskScope и запускает две подзадачи, затем ожидает в методе join и объединяет результаты обеих подзадач. Если код, выполняемый потоками, в которых работают subtask1 и subtask2, использует ScopedValue.get() для получения значения USERNAME, будет возвращено значение «duke».
private static final ScopedValue<String> USERNAME = ScopedValue.newInstance();
MyResult result = ScopedValue.where(USERNAME, "duke").call(() -> {
try (var scope = StructuredTaskScope.open()) {
Subtask<String> subtask1 = scope.fork( .. ); // inherits binding
Subtask<Integer> subtask2 = scope.fork( .. ); // inherits binding
scope.join();
return new MyResult(subtask1.get(), subtask2.get());
}
});
Унаследованное подзадачей значение области видимости можно повторно привязать к новому значению в подзадаче на ограниченный период выполнения некоторого метода. По завершении метода значение ScopedValue возвращается к предыдущему значению — унаследованному от потока, выполняющего задачу.
Подзадача может выполнять код, который сам открывает новую StructuredTaskScope. Задача, выполняющаяся в потоке T1, открывает StructuredTaskScope и запускает подзадачу, работающую в потоке T2. Привязки значений области видимости, зафиксированные при открытии области потоком T1, наследуются потоком T2. Подзадача (в потоке T2) выполняет код, который открывает новую StructuredTaskScope и запускает подзадачу, работающую в потоке T3. Привязки значений области видимости, зафиксированные при открытии области потоком T2, наследуются потоком T3. Они включают привязки, унаследованные от T1, или могут совпадать с ними. По сути, значения области видимости наследуются деревом подзадач, а не только одним уровнем подзадач.
Эффекты согласованности памяти
Действия в потоке-владельце StructuredTaskScope, предшествующие запуску подзадачи, происходят до любых действий, выполняемых этой подзадачей; в свою очередь, они происходят до полученияПРЕДВАРИТЕЛЬНАЯ ВЕРСИЯ результата подзадачи.
Общие исключения
Если не указано иное, передача аргумента null в метод этого класса приводит к выбрасыванию NullPointerException.
- См. Спецификацию языка Java:
- 17.4.5 Порядок happens-before
- Начиная с:
- 21
Краткое описание вложенных классов
| Модификатор и тип | Интерфейс | Описание |
|---|---|---|
static interface |
StructuredTaskScope.ConfigurationPREVIEW |
Предварительная версия. Представляет конфигурацию для StructuredTaskScope. |
static final class |
StructuredTaskScope.FailedExceptionPREVIEW |
Предварительная версия. Исключение, выбрасываемое методом join(), если исходом является исключение, а не результат. |
static interface |
StructuredTaskScope.JoinerPREVIEW<T, |
Предварительная версия. Объект, используемый с StructuredTaskScopeПРЕДВАРИТЕЛЬНАЯ ВЕРСИЯ для обработки завершения подзадач и формирования результата для владельца области, ожидающего в методе join завершения подзадач. |
static interface |
StructuredTaskScope.SubtaskPREVIEW<T> |
Предварительная версия. Представляет подзадачу, запущенную с помощью fork(Callable) или fork(Runnable). |
static final class |
StructuredTaskScope.TimeoutExceptionPREVIEW |
Предварительная версия. Исключение, выбрасываемое методом join(), если область создана с ограничением времени ожидания и срок истёк до ожидания в join или во время него. |
Краткое описание методов
| Модификатор и тип | Метод | Описание |
|---|---|---|
void |
close() |
Закрывает эту область. |
<U extends T> |
fork |
Запускает подзадачу, создавая в этой области новый поток для выполнения метода, не возвращающего результат. |
<U extends T> |
fork |
Запускает подзадачу, создавая в этой области новый поток для выполнения метода, возвращающего значение. |
boolean |
isCancelled() |
Возвращает true, если эта область отменена или процесс её отмены уже начался; в противном случае возвращает false. |
R |
join() |
Возвращает результат или выбрасывает исключение после ожидания завершения всех подзадач либо отмены области. |
static <T> StructuredTaskScopePREVIEW |
open() |
Открывает новую StructuredTaskScope, которую можно использовать для запуска подзадач, возвращающих результаты любого типа. |
static <T, |
open |
Открывает новую StructuredTaskScope для использования указанного объекта Joiner. |
static <T, |
open |
Открывает новую StructuredTaskScope для использования указанного объекта Joiner и конфигурации, полученной в результате применения заданной функции к конфигурации по умолчанию. |
Подробное описание методов
open
static <T,R> StructuredTaskScopePREVIEW<T,R> open(StructuredTaskScope.JoinerPREVIEW<? super T, ? extends R> joiner, Function<StructuredTaskScope.ConfigurationPREVIEW, StructuredTaskScope.ConfigurationPREVIEW> configFunction)
StructuredTaskScope для использования указанного объекта Joiner и с конфигурацией, полученной в результате применения указанной функции к конфигурации по умолчанию. configFunction вызывается с конфигурацией по умолчанию и возвращает конфигурацию для новой области. Например, функция может задать ThreadFactoryPREVIEW или задать время ожиданияPREVIEW. Если выполнение функции завершается исключением или ошибкой, они передаются этим методом. Если функция возвращает null, выбрасывается NullPointerException.
Если задан ThreadFactory, для создания потоков при запуске подзадач в этой области будет вызван его метод newThread. Если ThreadFactory не задан, при запуске подзадач для каждой из них будет создан безымянный виртуальный поток.
Если задано время ожиданияPREVIEW, его отсчёт начинается при открытии области. Если время ожидания истекает до того, как область будет объединена, область отменяется, а метод join выбрасывает StructuredTaskScope.TimeoutExceptionPREVIEW.
Новая область принадлежит текущему потоку. Только код, выполняющийся в этом потоке, может запускать подзадачи, вызывать объединение или закрывать область.
При создании фиксируются привязки ограниченных значений текущего потока для наследования потоками, запущенными в области.
- Параметры типа:
T— тип результата подзадач, выполняемых в областиR— тип результата области- Параметры:
-
joiner— объединитель -
configFunction— функция для создания конфигурации - Возвращает:
- новую область
- Начиная с версии:
- 25
open
static <T,R> StructuredTaskScopePREVIEW<T,R> open(StructuredTaskScope.JoinerPREVIEW<? super T, ? extends R> joiner)
StructuredTaskScopeдля использования указанного объекта Joiner. Область создаётся с конфигурацией по умолчанию. В конфигурации по умолчанию задан ThreadFactory, который создаёт безымянные виртуальные потоки; область не имеет имени для целей мониторинга и управления и не имеет времени ожидания.- Требования к реализации:
- Этот фабричный метод эквивалентен вызову двухаргументного метода open с указанным объединителем и тождественной функцией.
- Параметры типа:
T— тип результата подзадач, выполняемых в областиR— тип результата области- Параметры:
-
joiner— объединитель - Возвращает:
- новую область
- Начиная с версии:
- 25
open
static <T> StructuredTaskScopePREVIEW<T,Void> open()
StructuredTaskScope, которую можно использовать для запуска подзадач, возвращающих результаты любого типа. Метод join() области ожидает успешного завершения всех подзадач или сбоя любой подзадачи. Метод join возвращает null, если все подзадачи завершились успешно. Если какая-либо подзадача завершилась с ошибкой, он выбрасывает StructuredTaskScope.FailedExceptionPREVIEW; причиной служит исключение первой завершившейся с ошибкой подзадачи.
Область создаётся с конфигурацией по умолчанию. В конфигурации по умолчанию задан ThreadFactory, который создаёт безымянные виртуальные потоки; область не имеет имени для целей мониторинга и управления и не имеет времени ожидания.
- Требования к реализации:
- Этот фабричный метод эквивалентен вызову двухаргументного метода open с объединителем, созданным с помощью
awaitAllSuccessfulOrThrow()PREVIEW, и тождественной функции. - Параметры типа:
T— тип результата подзадач- Возвращает:
- новую область
- Начиная с версии:
- 25
fork
<U extends T> StructuredTaskScope.SubtaskPREVIEW<U> fork(Callable<? extends U> task)
Callable; новый поток выполняет его метод call(). Сначала этот метод создаёт объект SubtaskPREVIEW, представляющий запущенную подзадачу. Он вызывает метод объединителя onForkPREVIEW, передавая подзадачу в состоянии UNAVAILABLEPREVIEW. Если выполнение onFork завершается исключением или ошибкой, они передаются методом fork без создания потока. Если область уже отменена или onFork возвращает true для отмены области, этот метод возвращает Subtask в состоянии UNAVAILABLEPREVIEW и не создаёт поток для выполнения подзадачи.
Если область не отменена и метод onFork возвращает false, создаётся и запускается поток с использованием ThreadFactory, заданного при открытии области. При запуске подзадача наследует привязки ограниченных значений текущего потока. Эти привязки должны совпадать с привязками, зафиксированными при открытии области. Если подзадача завершается (успешно или с исключением) до отмены области, поток вызывает метод объединителя onCompletePREVIEW, передавая подзадачу в состоянии SUCCESSPREVIEW или FAILEDPREVIEW. Если выполнение метода onComplete завершается исключением или ошибкой, перед завершением потока вызывается обработчик неперехваченных исключений, которому передаётся это исключение или ошибка.
Этот метод возвращает объект SubtaskPREVIEW. В некоторых случаях этот объект можно использовать для получения результата. В других случаях его можно использовать для сопоставления или отбросить. Чтобы обеспечить корректное использование, метод Subtask.get()PREVIEW может вызываться владельцем области только для получения результата после ожидания завершения подзадач с помощью метода join и успешного завершения подзадачи. Аналогично, метод Subtask.exception()PREVIEW может вызываться владельцем области только после объединения, если подзадача завершилась с ошибкой. Если область была отменена до запуска подзадачи или до её завершения, ни один из этих методов нельзя использовать для получения результата.
Этот метод может вызываться только владельцем области.
- Параметры типа:
U— тип результата- Параметры:
-
task— задача, возвращающая значение, для выполнения в потоке - Возвращает:
- подзадачу
- Выбрасывает:
-
WrongThreadException— если текущий поток не является владельцем области -
IllegalStateException— если владелец уже выполнил объединение или область закрыта -
StructureViolationExceptionPREVIEW— если текущие привязки ограниченных значений не совпадают с привязками на момент создания области -
RejectedExecutionException— если фабрика потоков отказала в создании потока для выполнения подзадачи
fork
<U extends T> StructuredTaskScope.SubtaskPREVIEW<U> fork(Runnable task)
Этот метод работает точно так же, как fork(Callable), за исключением того, что его параметр — Runnable, новый поток выполняет его метод run, а метод Subtask.get()PREVIEW возвращает null, если подзадача завершается успешно.
- Параметры типа:
U— тип результата- Параметры:
-
task— задача для выполнения в потоке - Возвращает:
- подзадачу
- Выбрасывает:
-
WrongThreadException— если текущий поток не является владельцем области -
IllegalStateException— если владелец уже выполнил объединение или область закрыта -
StructureViolationExceptionPREVIEW— если текущие привязки ограниченных значений не совпадают с привязками на момент создания области -
RejectedExecutionException— если фабрика потоков отказала в создании потока для выполнения подзадачи - Начиная с версии:
- 25
join
R join() throws InterruptedException
Этот метод ожидает завершения всех подзадач, запущенных в этой области, или отмены области. Если настроено время ожиданияPREVIEW и оно истекает до начала ожидания или во время него, область отменяется, а метод выбрасывает TimeoutExceptionPREVIEW. После завершения ожидания вызывается метод result()PREVIEW объекта Joiner, чтобы получить результат или выбросить исключение. Если метод result() выбрасывает исключение, этот метод выбрасывает FailedException, указав это исключение в качестве причины.
Этот метод может быть вызван только владельцем области и только один раз.
- Возвращает:
- результат
- Выбрасывает:
-
WrongThreadException— если текущий поток не является владельцем области -
IllegalStateException— если объединение уже выполнено или эта область закрыта -
StructuredTaskScope.FailedExceptionPREVIEW— если результатом является исключение; оно выбрасывается с исключением изJoiner.result()PREVIEW в качестве причины -
StructuredTaskScope.TimeoutExceptionPREVIEW— если задано время ожидания и оно истекает до начала ожидания или во время него -
InterruptedException— если во время ожидания возникает прерывание - Начиная с версии:
- 25
isCancelled
boolean isCancelled()
true, если эта область отменена или выполняется её отмена; в противном случае возвращает false. Отмена области запрещает запуск новых потоков в ней и прерывает потоки, выполняющие незавершённые подзадачи. Для завершения выполнения прерванных потоков может потребоваться некоторое время; этот метод может вернуть true до прерывания всех потоков или до их завершения.
- Примечание API:
- Задача с длительной «фазой запуска» (кодом, выполняемым до вызова
join) может использовать этот метод, чтобы не выполнять работу в случаях, когда область отменяется из-за завершения ранее запущенной подзадачи или истечения времени ожидания. - Возвращает:
-
true, если эта область отменена или выполняется её отмена; в противном случае возвращаетfalse - Начиная с версии:
- 25
close
void close()
Сначала этот метод отменяет область, если она ещё не отменена. При этом прерываются потоки, выполняющие незавершённые подзадачи. Затем метод ожидает завершения всех потоков. Если во время ожидания возникает прерывание, ожидание продолжается до завершения потоков, после чего метод завершается с установленным статусом прерывания.
Этот метод может вызываться только владельцем области. Если область уже закрыта, вызов этого метода владельцем области не оказывает никакого эффекта.
Предполагается, что StructuredTaskScope используется структурированным образом. Если этот метод вызывается для закрытия области до закрытия вложенных областей задач, он закрывает базовую конструкцию каждой вложенной области (в порядке, обратном порядку их создания), закрывает эту область, а затем выбрасывает StructureViolationExceptionPREVIEW. Аналогично, если этот метод вызывается для закрытия области при выполнении с привязками ограниченных значений, а область была создана до привязки ограниченных значений, после закрытия области выбрасывается StructureViolationException. Если поток завершается, не закрыв предварительно принадлежащие ему области, завершение потока приводит к закрытию базовой конструкции каждой из его открытых областей задач. Закрытие выполняется в порядке, обратном порядку создания областей. Поэтому завершение потока может задержаться, если владельцу области необходимо дождаться завершения потоков, запущенных в этих областях.
- Указано в:
-
closeв интерфейсеAutoCloseable - Выбрасывает:
-
IllegalStateException— выбрасывается после закрытия области, если владелец области не пытался выполнить объединение после запуска подзадач -
WrongThreadException— если текущий поток не является владельцем области -
StructureViolationExceptionPREVIEW— если обнаружено нарушение структуры
© 1993, 2025, 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/25/docs/api/java.base/java/util/concurrent/StructuredTaskScope.html
StructuredTaskScope, только если включены функции предварительной версии.