LockSupport - это базовая потока, блокирующая примитив, используемый для создания замков и других классов синхронизации.
Функции Park () и unpark () в LockSupport заключаются в блокировании потоков и разблокировочных потоков соответственно, а Park () и unpark () не столкнутся с «тупиками, которые могут быть вызваны тем.
Потому что парк () и unpark () имеют разрешения; Конкуренция между The Thread Calling Park () и другой веткой, пытающейся unpark (), останется активной.
Основное использование
Локсапорт очень похож на двоичный семафор (доступно только 1 лицензия). Если эта лицензия не была занята, текущая поток получает лицензию и продолжает выполнять; Если лицензия была занята, текущие потоки блокируются, ожидая получения лицензии.
public static void main (string [] args) {locksupport.park (); System.out.println ("block.");}Запуск кода покажет, что основной поток всегда блокируется. Поскольку лицензия занята по умолчанию, лицензия не может быть получена при вызове парка (), поэтому она входит в состояние блокировки.
Следующий код: сначала выпустите лицензию, затем получите лицензию, и основной поток может нормально прекращаться. Приобретение и выпуск лицензий с лосьпорным обеспечением, как правило, соответствуют. Если вы не выберите несколько раз, не будет проблем, если вы паркуете только один раз. В результате лицензия находится в доступном состоянии.
public static void main (string [] args) {thread = Thread.currentThread (); Locksupport.unpark (thread); // Выпустить лицензию locksupport.park (); // получить лицензионную систему.out.println ("b");}Локсопорт не повторно. Если поток вызывает LockSupport .park () дважды в ряду, то поток обязательно заблокируется.
public static void main (string [] args) выбрасывает exection {thread = thread.currentThread (); Locksupport.unpark (нить); System.out.println ("a"); Locksupport.park (); System.out.println ("b"); Locksupport.park (); System.out.println ("c");}Этот код печатает A и B, но не печатает C, потому что поток не может получить разрешение при вызове парка во второй раз.
Давайте посмотрим на реакцию соответствующих прерываний LockSupport
public static void T2 () Throws Exception {Thread T = New Thread (new Runnable () {private int count = 0; @Override public void run () {long start = system.currenttimemillis (); long end = 0; while ((end - start) <= 1000) {count ++; end = system.currentTimilis (); + count); t.start (); Thread.sleep (2000); // прерывать поток t.interrupt (); System.out.println ("Main Over");}Поток распечатает поток Over.true. Это означает, что если поток блокирует вызов парка, он может ответить на запрос прерывания (статус прерывания устанавливается на True), но не будет выбросить прерывание.
Список функций LockSupport
// Возвращает объект блокировщика, предоставленную последнему разблокированному вызову метода парка, и возвращает NULL, если вызов не заблокирован. Статический объект getBlocker (поток T) // Для планирования потоков отключите текущий поток, если лицензия не доступна. Static void Park () // Для планирования резьбы отключите текущую потоку до доступной лицензии. Static void Park (блокировщик объектов) // Для планирования потоков подождите наиболее указанное время ожидания, если лицензия не доступна. Статические пустоты Parknanos (Long Nanos) // Для планирования потоков отключите текущий поток до того, как лицензия будет доступна, и ожидайте указанного времени ожидания. Статический void parknanos (блокировщик объектов, длинные нано) // Для планирования потоков текущий поток отключен до указанного срока, если лицензия не будет доступна. Статический void parkuntil (длинный крайний срок) // Для планирования потоков текущий поток отключен до указанного срока, если лицензия не будет доступна. Статический void parkuntil (блокировщик объектов, длительный крайний срок) // Сделайте его доступным, если лицензия данного потока еще недоступна. Статический void unpark (потока)
Пример LockSupport
Сравнение «Пример 1» и «Пример 2» ниже может дать вам более четкое представление об использовании слесаря.
Пример 1
открытый класс waitTest1 {public static void main (string [] args) {threada ta = new threada ("ta"); синхронизированный (ta) {// Получить "блокировка синхронизации объекта Ta" через Synchronized (ta) try {System.out.println (thread.currentThread (). getName ()+"start ta"); ta.start (); System.out.println (think.currentThread (). GetName ()+"block"); // Основной поток ждет TA.Wait (); System.out.println (think.currentThread (). GetName ()+"Продолжение"); } catch (прерванное искусство e) {e.printstacktrace (); } / } public void run () {synchronized (this) {// Получить "блокировку синхронизации текущего объекта" через Synchronized (this) System.out.println (thread.currentThread (). getName ()+"Wakup другие"); notify (); // Просыпаться «Поток ожидания на текущем объекте»}}}} Пример 2
import java.util.concurrent.locks.locksupport; public class locksupporttest1 {private static thread mainthread; public static void main (string [] args) {threata ta = new threada ("ta"); // Получить основную потоку mainThread = thread.currentThread (); System.out.println (thread.currentThread (). GetName ()+"start ta"); ta.start (); System.out.println (think.currentThread (). GetName ()+"block"); // Основная резьба блокирует locksupport.park (mainthread); System.out.println (think.currentThread (). GetName ()+"Продолжение"); } static class Threada extends Thread {public Threata (String name) {super (name); } public void run () {System.out.println (think.currentThread (). getName ()+"wakup erese"); // Пробуждение "Главная нить" locksupport.unpark (mainthread); }}} Результаты работы:
Главный старт Tamain Blockta wakup Другие - продолжить
Описание: Разница между парком и ожиданием. Перед потоками блоков ожидания блокировка синхронизации должна быть получена посредством синхронизации.