Spec-Zone.ru › Perl 5.38

Поток

СОДЕРЖАНИЕ

  • НАЗВАНИЕ
  • УСТАРЕВШИЙ
  • ИСТОРИЯ
  • СИНОПСИС
  • ОПИСАНИЕ
  • ФУНКЦИИ
  • МЕТОДЫ
  • НЕДЕЙСТВУЮЩИЕ
  • СМОТРИТЕ ТАКЖЕ

НАЗВАНИЕ

Thread - Управление потоками в 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 0, а последующие потоки будут иметь присвоенные tid, начиная с 1.

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–2023 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.38.0/Thread

Spec-Zone.ru

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