Поток
СОДЕРЖАНИЕ
ИМЯ
Поток - Управление потоками в Perl (только для старого кода)
УСТАРЕВШИЙ
Модуль Thread служил передним интерфейсом для старой модели потоков, называемой 5005threads, которая была представлена в релизе 5.005. Эта модель устарела и была удалена в версии 5.10.
Для старого кода и временной обратной совместимости модуль Thread был переработан, чтобы функционировать как интерфейс для новой модели потоков интерпретатора (ithreads). Однако некоторые предыдущие функции недоступны. Кроме того, модели обмена данными между двумя моделями потоков совершенно разные, и всё, что связано с обменом данными, нужно рассматривать по-другому. С помощью ithreads вы должны явно share() переменные между потоками.
Настоятельно рекомендуется как можно скорее перенести любой существующий многопоточный код на новую модель (то есть использовать модули threads и threads::shared).
ИСТОРИЯ
В Perl 5.005 модель потоков предполагала, что все данные неявно общие, а общий доступ к данным необходимо явно синхронизировать. Эта модель называется 5005threads.
В Perl 5.6 была представлена новая модель, в которой все данные были локальными для потока, а общий доступ к данным необходимо было явно объявить. Эта модель называется ithreads (потоки интерпретатора).
В Perl 5.6 модель ithreads была недоступна как общедоступный API; она была доступна только как внутренний API для разработчиков расширений и для реализации эмуляции fork() на платформах Win32.
В Perl 5.8 модель ithreads стала доступна через модуль threads , а модель 5005threads устарела.
В Perl 5.10 модель 5005threads была удалена из интерпретатора Perl.
СИНОПСИС
use Thread qw(:DEFAULT async yield);
my $t = Thread->new(\&start_sub, @start_args);
$result = $t->join;
$t->detach;
if ($t->done) {
$t->join;
}
if($t->equal($another_thread)) {
# ...
}
yield();
my $tid = Thread->self->tid;
lock($scalar);
lock(@array);
lock(%hash);
my @list = Thread->list; ОПИСАНИЕ
Модуль Thread обеспечивает поддержку многопоточности для Perl.
ФУНКЦИИ
- $thread = Thread->new(\&start_sub)
- $thread = Thread->new(\&start_sub, LIST)
-
newзапускает новый поток выполнения в указанной подпрограмме. Необязательный список передаётся в качестве параметров подпрограмме. Выполнение продолжается как в подпрограмме, так и в коде после вызоваnew.Thread->newвозвращает объект потока, представляющий вновь созданный поток. - lock VARIABLE
-
lockустанавливает блокировку на переменной до выхода из области видимости.Если переменная заблокирована другим потоком, вызов
lockбудет приостановлен до тех пор, пока она не станет доступной.lockрекурсивный, поэтому многократные вызовыlockбезопасны — переменная останется заблокированной до выхода из области видимости самой внешней блокировки на переменной.Блокировки на переменных влияют только на вызовы
lock— они не влияют на обычный доступ к переменной. (Блокировки на подпрограммах отличаются и будут рассмотрены позднее.) Если вам действительно, очень нужны блокировки для блокировки доступа, создайте их привязку к чему-нибудь и управляйте этим самостоятельно. Это сделано намеренно. Хотя управление доступом к переменным — это хорошо, Perl не выгонит вас из своей комнаты...Если заблокирован контейнерный объект, например, массив или хеш, все элементы этого контейнера не блокируются. Например, если один поток выполняет
lock @a, любой другой поток, выполняющийlock($a[12]), не будет приостановлен.Наконец,
lockбудет переходить по ссылкам ровно на один уровень.lock(\$a)эквивалентноlock($a), аlock(\\$a)— нет. - async BLOCK;
-
asyncсоздаёт поток для немедленного выполнения блока кода, который следует за ним. Этот блок рассматривается как анонимная подпрограмма, поэтому после закрывающей фигурной скобки должен стоять точка с запятой. ПодобноThread->new,asyncвозвращает объект потока. - Thread->self
-
Функция
Thread->selfвозвращает объект потока, представляющий поток, совершающий вызовThread->self. - Thread->list
-
Возвращает список всех не присоединённых и не отсоединённых объектов потока Thread.
- cond_wait VARIABLE
-
Функция
cond_waitпринимает заблокированную переменную в качестве параметра, разблокирует переменную и останавливается до тех пор, пока другой поток не выполнитcond_signalилиcond_broadcastдля той же заблокированной переменной. Переменная, на которойcond_waitостановился, вновь блокируется после выполненияcond_wait. Если несколько потоковcond_waitзаблокированы на одной переменной, все, кроме одного, будут повторно приостановлены в ожидании повторного получения блокировки на переменной. (Поэтому, если вы используетеcond_waitтолько для синхронизации, как можно скорее отпустите блокировку.) - cond_signal VARIABLE
-
Функция
cond_signalпринимает заблокированную переменную в качестве параметра и разблокирует один из заблокированных потоков, который находится в ожиданииcond_waitна этой переменной. Если несколько потоков находятся в ожиданииcond_waitна этой переменной, только один (и какой — не определено) будет разблокирован.Если потоки не находятся в ожидании
cond_waitна переменной, сигнал игнорируется. - cond_broadcast VARIABLE
-
Функция
cond_broadcastработает аналогичноcond_signal.cond_broadcast, однако, разблокирует все потоки, которые находятся в ожиданииcond_waitна заблокированной переменной, а не только один. - yield
-
Функция
yieldпозволяет другому потоку взять под контроль процессор. Точные результаты зависят от реализации.
МЕТОДЫ
- join
-
joinожидает завершения потока и возвращает любые значения, с которыми поток завершился.joinбудет приостановлен до тех пор, пока поток не завершится, хотя он не будет приостановлен, если поток уже завершён.Если поток, на котором выполняется
join,die, возвращается ошибка, с которой он завершился. Если вы не хотите, чтобы поток, выполняющийjoin, завершился с ошибкой, вы должны либо заключитьjoinвeval, либо использовать метод потокаevalвместоjoin. - detach
-
detachсообщает потоку, что он никогда не будет присоединяться, то есть все следы его существования могут быть удалены после его остановки. Ошибки в отсоединённых потоках нигде не будут видны — если вы хотите их перехватить, вы должны использовать $SIG{__DIE__} или что-то подобное. - equal
-
equalпроверяет, представляют ли два объекта потока один и тот же поток, и возвращает true, если это так. - tid
-
Метод
tidвозвращает tid потока. Tid — это монотонно возрастающее целое число, присваиваемое при создании потока. У основного потока программы tid будет равен нулю, а у последующих потоков tids будут присваиваться, начиная с единицы. - done
-
Метод
doneвозвращает true, если поток, который вы проверяете, завершился, и false в противном случае.
УДАЛЁННЫЕ
Следующие функции были реализованы с помощью 5005threads, но больше не доступны с помощью ithreads.
- lock(\&sub)
-
В 5005threads вы также могли
lockподпрограмму таким образом, что любые вызовы этой подпрограммы из другого потока будут блокироваться до тех пор, пока блокировка не будет освобождена.Также подпрограммы могли быть объявлены с атрибутом
:locked, который бы сериализовал доступ к подпрограмме, но позволял разным потокам получать к ней неодновременный доступ. - eval
-
Метод
evalзаключалevalвокругjoin, и поэтому ожидал завершения потока, передавая любые значения, которые мог вернуть поток, и помещая любые ошибки в$@. - flags
-
Метод
flagsвозвращал флаги потока — целочисленное значение, соответствующее внутренним флагам потока.
СМОТРИТЕ ТАКЖЕ
threads, threads::shared, Thread::Queue, Thread::Semaphore
© 1993–2020 Larry Wall and others
Licensed under the GNU General Public License version 1 or later, or the Artistic License.
The Perl logo is a trademark of the Perl Foundation.
https://perldoc.perl.org/5.30.3/Thread