Как настроить смартфоны и ПК. Информационный портал

Приложение. Основы ActionScript

Для того чтобы иметь возможность реализовать логику в программе используются условные операторы. Умозрительно эти операторы можно представить в виде узловых пунктов, достигая которых программа делает выбор по какому из возможных направлений двигаться дальше. Например, требуется определить, содержит ли некоторая переменная arg положительное или отрицательное число и вывести соответствующее сообщение на экран. Для этого можно воспользоваться оператором if (если), который и выполняет подобные проверки.

В самом простом случае синтаксис данного оператора if следующий:

if (выражение)

Если значение параметра «выражение» равно «истинно», выполняется оператор, иначе он пропускается программой. Следует отметить, что «выражение» является условным выражением, в котором выполняется проверка некоторого условия. В табл. 2.1 представлены варианты простых логических выражений оператора if.

Таблица 2.1. Простые логические выражения

Приведем пример использования оператора ветвления if. Следующая программа позволяет определять знак введенной переменной.

Листинг 2.1. Первая программа определения знака введенного числа.

#include
int main()
{
float x;
printf(“Введите число: ”);
scanf(“%f”,&x);
if(x >= 0)

Return 0;
}

Анализ приведенного текста программы показывает, что два условных оператора можно заменить одним, используя конструкцию

if (выражение)

которая интерпретируется таким образом. Если «выражение» истинно, то выполняется «оператор1», иначе выполняется «оператор2». Перепишем ранее приведенный пример определение знака числа с использованием данной конструкции.

Листинг 2.2. Вторая программа определения знака введенного числа.

#include
int main()
{
float x;
printf(“Введите число: ”);
scanf(“%f”,&x);
if(x printf(“Введенное число %f является отрицательным.\n”, x);
else
printf(“Введенное число %f является неотрицательным.\n”, x);

Return 0;
}

В представленных примерах после операторов if и else стоит всего одна функция printf(). В случаях, когда при выполнении какого-либо условия необходимо записать более одного оператора, необходимо использовать фигурные скобки, т.е. использовать конструкцию вида

if (выражение)
{

}
else
{

Следует отметить, что после ключевого слова else формально можно поставить еще один оператор условия if, в результате получим еще более гибкую конструкцию условных переходов:

if(выражение1)
else if(выражение2)
else

На листинге 2.3 представлена программа, реализующая последнюю конструкцию условных переходов.

Листинг 2.3. Третья программа определения знака введенного числа.

#include
int main()
{
float x;
printf(“Введите число: ”);
scanf(“%f”,&x);
if(x printf(“Введенное число %f является отрицательным.\n”, x);
else if(x > 0)
printf(“Введенное число %f является положительным.\n”, x);
else
printf(“Введенное число %f является неотрицательным.\n”,x);

Return 0;
}

До сих пор рассматривались простые условия типа x && - логическое И
|| - логическое ИЛИ
! – логическое НЕТ

На основе этих трех логических операций можно сформировать более сложные условия. Например, если имеются три переменные exp1, exp2 и exp3, то они могут составлять логические конструкции, представленные в табл. 2.2.

Таблица 2.2. Пример составных логических выражений

Подобно операциям умножения и сложения в математике, логические операции И ИЛИ НЕТ, также имеют свои приоритеты. Самый высокий приоритет имеет операция НЕТ, т.е. такая операция выполняется в первую очередь. Более низкий приоритет у операции И, и наконец самый малый приоритет у операции ИЛИ. Данные приоритеты необходимо учитывать, при составлении сложных условий. Например, условие

if(4 6 || 5 проверяется таким образом. Если 4 6 ИЛИ 5 if(4 6 || 5 Условная операция if облегчает написание программ, в которых необходимо производить выбор между небольшим числом возможных вариантов. Однако иногда в программе необходимо осуществить выбор одного варианта из множества возможных. Формально для этого можно воспользоваться конструкцией if else if … else. Однако во многих случаях оказывается более удобным применять оператор switch языка С++. Синтаксис данного оператора следующий:

switch(переменная)
{
case константа1:

Case константа2:

...
default:

Данный оператор последовательно проверяет на равенство переменной константам, стоящим после ключевого слова case. Если ни одна из констант не равна значению переменно, то выполняются операторы, находящиеся после слова default. Оператор switch имеет следующую особенность. Допустим, значение переменной равно значению константы1 и выполняются операторы, стоящие после первого ключевого слова case. После этого выполнение программы продолжится проверкой переменной на равенство константы2, что часто приводит к неоправданным затратам ресурсов ЭВМ. Во избежание такой ситуации следует использовать оператор break для перехода программы к следующему оператору после switch.

На листинге 2.4 представлен пример программирования условного оператора switch.

Листинг 2.4. Пример использования оператора switch.

#include
int main()
{
int x;
printf(“Введите число: ”);
scanf(“%d”,&x);
switch(x)
{
case 1: printf(“Введено число 1\n”);break;
case 2: printf(“Введено число 2\n”); break;
default: printf(“Введено другое число\n”);
}
char ch;
printf(“Введите символ: ”);
scanf(“%с”,&сh);
switch(ch)
{
case ‘a’ : printf(“Введен символ а\n”); break;
case ‘b’ : printf(“Введен символ b\n”); break;
default: printf(“Введен другой символ\n”);
}
return 0;
}

Данный пример демонстрирует два разных варианта использования оператора switch. В первом случае выполняется анализ введенной цифры, во втором – анализ введенного символа. Следует отметить, что данный оператор может производить выбор только на основании равенства своего аргумента одному из перечисленных значений case, т.е. проверка выражений типа x

Можно хранить знания о собеседниках или любую другую текстовую информацию. Сейчас при написании шаблонов можно использовать 13 переменных , имеющих заранее заданное целевое назначение, и 100 "свободных", которые владельцы инфов могут использовать по своему усмотрению.
Переменные с заданным целевым назначением имеют «говорящие» имена. Например, %user_name – это переменная , предназначенная для хранения имени собеседника. В ее имени употреблены английские слова user ("пользователь") и name ("имя"). Такие переменные активно используются разработчиками при создании базы шаблонов стандартного инфа , на основе которого в проекте создаются все пользовательские инфы .
Срок жизни таких переменных не ограничен, т.е. их значения запоминаются и хранятся между отдельными разговорами.

Что написано в шаблонах Пример диалога
Запоминаем имя:
$ Меня зовут *
# Рад познакомиться. [%user_name="[*1]"]
Гость: Меня зовут Вася
Инф: Раз познакомиться.
Выводим имя собеседника в ответ инфа:
$ Пока, инф.
# До свидания, [%user_name]
Гость: Пока, инф.
Инф: До свидания, Вася.
Выбираем ответ в зависимости от значения переменной %user_name:
$ Ты помнишь, как меня зовут?
# {Конечно. Ты [%user_name].}
# {Нет. Ты свое имя мне не называл.}
Гость: Ты помнишь, как меня зовут?
Инф: Конечно. Ты Вася.
или
Гость: Ты помнишь, как меня зовут?
Инф: Нет. Ты свое имя мне не называл.
Не хотим больше хранить имя собеседника, обнуляем переменную
$ Ты дурак.
# Все, я с тобой больше не дружу, и забыл, как тебя зовут. [%user_name=""]
Гость: Ты дурак.
Инф: Все, я с тобой больше не дружу, и забыл, как тебя зовут.

Присвоение значения переменной и обнуление переменной

Присвоить значение переменной или обнулить ее можно в ответах инфа.

Синтаксис: [%переменная = "значение"]
Команда присвоения переменной всегда окружается квадратными скобками, которые здесь являются служебными символами. Значение переменной всегда стоит в кавычках.
Примеры присвоения значения:
$ Я рок-н-ролл танцую.
# Завидую. Инфы танцевать не могут [%var1="танцы"]

$ * ненавижу * танцевать *
$ * танцевать * ненавижу *
$ * не танцую *
# Жаль. Будь я человеком, обязательно бы танцевала. [%var1="не любит танцы"]

$ Мне ** лет.
# Классный возраст! [%user_age="[*1]"]

Пример обнуления переменной :
$ Не хочу, чтобы ты говорил про мой возраст.
# Как скажешь [%user_age=""]

Присвоение значения переменной с помощью функции set

Функция set("Аргумент1", "Аргумент2", "Аргумент3") подставляет на своё место Аргумент2 и присваивает его значение переменной, указанной в Аргументе1. Аргумент3 по умолчанию равен пустой строке. Если его указать отличным от пустой строки, то на место функции set никакой текст подставлен не будет и произойдёт только присваивание значения переменной.

Например,
$ меня зовут **
#Приятно познакомиться, [@set("user_name", "[@ ("[*1]")]")]!

Гость: меня зовут вася
Инф: Приятно познакомиться, Вася!

Или:
$ меня зовут **
# Я запомню, как тебя зовут. [@set("user_name", "[@ ("[*1]")]", "1")]

$ * как * меня * зовут *
# Ты [%user_name].

Гость: меня зовут лена
Инф: Я запомню, как тебя зовут.
Гость: ну и как меня зовут?
Инф: Ты Лена.

Вывод значения переменной в ответе инфа

Для того, чтобы инф "озвучил" значение переменной в ответе, надо просто прописать в ответе эту переменную .
Синтаксис: [%переменная]
Квадратные скобки обязательны.

Пример:
$ Пока, робот!
# До свидания, [%user_name]!

Условную переменную можно использовать для реализации отношений синхронизации, о которых упоминалось выше: старт-старт (CC), финиш-старт (ФС), старт-финиш (СФ) и финиш-финиш (ФФ). Эти отношения могут существовать между потоками одного или различных процессов. В листингах 5.4 и 5.5 представлены примеры реализации ФС- и ФФ-отношений синхронизации. В каждом примере определено два мьютекса. Один мьютекс используется для синхронизации доступа к общим данным, а другой - для синхронизации выполнения кода.

// Листинг 5.4. ФС-отношения синхронизации между

// двумя потоками

pthread_t ThreadA,ThreadB;

pthread_cond_t Event;

void * worker1 (void *X) {

for(int Count = l;Count

pthread_mutex_lock(&Mutex);

pthread_mutex_unlock(&Mutex);

if(Number == 50){

pthread_cond_signal(&Event);

void * worker2 (void *X) {

pthread_mutex_lock(&EventMutex);

pthread_cond_wait(&Event,&EventMutex);

for(int Count = 1;Count

pthread_mutex_lock(&Mutex);

Number = Number + 20;

pthread_mutex_unlock(&Mutex);

cout « «Выполнение функции worker2 завершено.» « endl; return(0);

int main (int argc, char *argv) {

pthread_mutex_init(&Mutex,NULL);

pthread_mutex_init(&EventMutex,NULL);

pthread_cond_init(&Event, NULL);

pthread_create(&ThreadA, NULL, workerl, NULL);

pthread_create(&ThreadB, NULL, worker2 , NULL);

В листинге 5.4 показан пример реализации ФС-отношений синхронизации. Поток ThreadA не может завершиться до тех пор, пока не стартует поток ThreadB. Если значение переменной Number станет равным 50, поток ThreadA сигнализирует о этом потоку ThreadB. Теперь он может продолжать выполнение до самого конца Поток ThreadB не может начать выполнение до тех пор, пока не получит сигнал от потока ThreadA. Поток ThreadB использует объект EventMutex вместе с условной переменной Event. Объект Mutex используется для синхронизации доступа для записи значения разделяемой переменной Number. Для синхронизации различных событий и доступа к критическим разделам задача может использовать несколько мьютексов.

Пример реализации ФФ-отношений синхронизации показан в листинге 5.5.

// Листинг 5.5. ФФ-отношения синхронизации между // двумя потоками

pthread_t ThreadA, ThreadB ;

pthread_mutex_t Mutex, EventMutex;

pthread_cond_t Event;

void *workerl(void *X) {

for(int Count = l;Count

pthread_mu tex_l ock (&Mutex);

pthread_mutex_unlосk(&Mutex);

cout « «workerl: число равно "

pthread_mutex_lock(&EventMutex) ,-

cout « «Функция workerl в состоянии ожидания. " « endl;

pthread_cond_wait (&Event, &EventMutex) ;

pthread_mutex_unlock(&EventMutex);

void *worker2 (void *X) {

for(int Count = l;Count

pthread_mutex_lock(&Mutex) ;

Number = Number * 2 ;

pthread_mutex_unlock(&Mutex) ;

cout « «worker2: число равно " « Number « endl;

pthread_cond_signal (&Event) ;

cout « «Функция worker2 послала сигнал " « endl; return(0);

int main(int argc, char *argv) {

pthread_mutex_init (&Mutex,NULL) ;

pthread_mutex_init (&EventMutex,NULL) ;

pthread_cond_init (&Event, NULL) ;

pthread_create(&ThreadA, NULL,workerl, NULL);

pthread_create (&ThreadB, NULL, worker2, NULL) ;

В листинге 5.5 поток ThreadA не может завершиться до тех пор, пока не завершится поток ThreadB. Поток ThreadA должен выполнить цикл 10 раз, а ThreadB - 100. Поток ThreadA завершит выполнение своих итераций раньше ThreadB, но будет ожидать до тех пор, пока поток ThreadB не просигналит о своем завершении.

CC- и СФ-отношения синхронизации невозможно реализовать подобным образом. Эти методы используются для синхронизации пор я дка выполнени я процессов.

ТАУ – теория автоматического управления

ТС – техническая система

ОУ- объект управления

УУ- управляющее устройство

СУ – система управления

ИО – исполнительный орган

ИУ – исполнительное устройство

Д – датчик

ОС – обратная связь

ПК – передаточный коэффициент

ПФ – передаточная функция

АФЧХ – амплитудно-фазовая частотная характеристика

АЧХ – амплитудно-частотная характеристика

ЛАЧХ – логарифмическая амплитудно-частотная характеристика

ФЧХ - фазо-частотная характеристика

2. Условные обозначения основных переменных и функций

x (t ) – входной сигнал элемента СУ, выходной сигнал ОУ и СУ (управляемая величина)

y (t ) – выходной сигнал элемента СУ, входной сигнал ОУ (управляющее воздействие)

x з (t ) – задающее воздействие СУ

z (t ) – возмущающее воздействие на СУ

(t ) – сигнал ошибки (рассогласования) в СУ

1(t ) – единичное ступенчатое воздействие

(t ) – единичное импульсное воздействие

x m ,y m амплитудные значения сигналовx (t ) иy (t )

p – оператор Лапласа, оператор дифференцирования

 - круговая частота, оператор преобразования Фурье

X (p ) – изображение непрерывного сигналаx (t ) по Лапласу

X (j ) – изображение непрерывного сигналаx (t ) по Фурье

k – ПК звена (или соединения звеньев)

W (p ) – ПФ звена (или соединения звеньев)

W (j ) – АФЧХ звена (или соединения звеньев)

А () – АЧХ звена (или соединения звеньев)

() – ФЧХ звена (или соединения звеньев)

Ф(р ) – ПФ замкнутой СУ

h (t ) – переходная функция (характеристика) звена или СУ

w (t ) – импульсная (весовая) функция (характеристика) звена или СУ

ВВЕДЕНИЕ

Теория автоматического управления (ТАУ) – научная дисциплина, предметом изучения которой являются информационные процессы, протекающие в системах управления техническими и технологическими объектами. ТАУ выявляет общие закономерности функционирования автоматических систем различной физической природы и на основе этих закономерностей разрабатывает принципы построения высококачественных систем управления.

При изучении процессов управления в ТАУ абстрагируются от физических и конструктивных особенностей систем и вместо реальных систем рассматривают их адекватные математические модели. Чем точнее (полнее) математическая модель соответствует физическим процессам, протекающим в реальной системе, тем совершеннее будет проектируемая система управления.

Основными методами исследования в ТАУ являются математическое моделирование, теория обыкновенных дифференциальных уравнений, операционное исчисление и гармонический анализ. Рассмотрим кратко каждый из них.

Метод математического моделирования , объединяющий самые разнообразные способы и приёмы описания и представления физических объектов и явлений, можно условно, схематично представить с помощью наиболее часто используемого приёма – графическим изображением простого объекта, имеющего один входной сигнал x (t ) и один выходной сигнал y (t ), в виде прямоугольника (рис. В. 1,а ). Символ А внутри прямоугольника означает некоторый математический оператор (функцию, интеграл и т. п.), который связывает входной и выходной сигналы, меняющиеся во времени.

Рис. В.1. Схематичное представление математических методов, используемых в ТАУ

Теория обыкновенных дифференциальных уравнений , акцентирующая своё внимание на физические аспекты и приложения получаемых решений, служит главной методологической основой ТАУ, а сами обыкновенные дифференциальные уравнения – наиболее общей и полной формой математического описания элементов и систем управления. Дифференциальные уравнения связывают меняющиеся во времени входные и выходные переменные и их производные. В простейшем случае дифференциальное уравнение имеет вид

dy (t )/dt =f [x (t ),y (t )]. (В.1)

Метод операционного исчисления , в основе которого лежит преобразование Лапласа

(В.2)

позволяет алгебраизировть дифференциальные уравнения – перейти к так называемым операторным уравнениям, связывающим изображения X (p ) и Y (p ) входного и выходного сигналов через передаточную функцию W (p ) (рис. В. 1,б )

W (p )=Y (p )/X (p ). (В.3)

Метод гармонического анализа основан на известном из курса математики преобразовании Фурье, имеющем вид

(В.4)

С помощью преобразования Фурье (В. 4) находят изображения X (j ) и Y (j ) входного и выходного сигналов x (t ) и y (t ), характеризующие частотные спектры этих сигналов. Изображения сигналов по Фурье связаны (рис.В. 1,в ) частотной передаточной функцией

W (j )=Y(j )/X(j ). (В.5)

Все четыре метода, кратко представленные выше, образуют математический аппарат ТАУ. На его базе разработан комплекс «собственных» методов ТАУ, излагаемых в настоящем курсе.

ТАУ вместе с теорией построения и функционирования элементов систем управления (датчиков, регуляторов, исполнительных устройств) образует более широкую отрасль науки – автоматику. Автоматика в свою очередь является одним из разделов технической кибернетики. Техническая кибернетика изучает сложные автоматизированные системы управления технологическими процессами (АСУТП) и предприятиями (АСУП), построенные с использованием управляющих вычислительных машин (УВМ).

Техническая кибернетика наряду с биологической и социоэкономической – составная часть кибернетики, которую её родоначальник, американский математик Н. Винер, в 1948 году определил как науку об управлении и связи в технических системах и живых организмах.

Первые промышленные регуляторы появились в период 1765-1804 гг. (И. Ползунов, Дж. Уатт, Ж. Жаккар).

Первые теоретические исследования регуляторов появились в период 1868-1893 гг. (Дж. Максвелл, И. Вышнеградский, А. Стодола). Российский учёный и инженер И. А. Вышнеградский выполнил ряд научных исследований, в которых паровая машина и её регулятор впервые были проанализированы математическими методами как единая динамическая система. В становлении российской школы ТАУ большую роль сыграли работы А. А. Андронова, В. С. Кулебакина, И. Н. Вознесенского, Б. В. Булгакова, А. А. Фельдбаума, Б. Н. Петрова, Н. Н. Красовского, А. А. Воронова, Я. З. Цыпкина, В. С. Пугачёва, …

Развитие современной теории управления из так называемой «классической» теории регулирования, основанной на четырёх вышеупомянутых основных методах исследования ТАУ, и формирование её новейших методов схематично проиллюстрированы на рис. В. 2.

Рис. В.2. Развитие содержания и методологии теории управления

В настоящее время ТАУ наряду с новейшими разделами общей теории управления (исследование операций, системотехника, теория игр, теория массового обслуживания) играет важнейшую роль в совершенствовании и автоматизации управления технологическими процессами и производствами.

Условные переменные

Условная переменная (condvar - сокращение от condition variable) используется для блокировки потока по какому-либо условию во время выполнения критической секции кода. Условие может быть сколь угодно сложным и не зависит от условной переменной. Однако условная переменная всегда должна использоваться совместно с мьютексом для проверки условия.

Условные переменные поддерживают следующие функции:

· ожидание условной переменной (wait) (pthread_cond_wait() );

· единичная разблокировка потока (signal) (pthread_cond_signal() )

· множественная разблокировка потока (broadcast) (pthread_cond_broadcast() ),

Приведем пример типичного использования условной переменной:

pthread_mutex_lock (&m) ;-…

while (!arbitrary condition) {

pthread_cond_wait(&cv, &m);

pthread_mutex_unlock (&m) ;

В этом примере захват мьютекса происходит до проверки условия. Таким образом, проверяемое условие применяется только к текущему потоку. Пока данное условие является истинным, эта секция кода блокируется на вызове ожидания до тех пор, пока какой-либо другой поток не выполнит операцию единичной или множественной разблокировки потока по условной переменной.

Цикл while в приведенном примере требуется по двум причинам. Во-первых, стандарты posix не гарантируют отсутствие ложных пробуждений (например, в многопроцессорных системах). Во-вторых, если другой поток изменяет условие, необходимо заново выполнить его проверку, чтобы убедиться, что изменение соответствует принятым критериям. При блокировании ожидающего потока связанный с условной переменной мутекс атомарно освобождается функцией pthread_cond_wait() для того, чтобы другой поток мог войти в критическую секцию программного кода.

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

Другой вид операции ожидания условной переменной (pthread__cond_timedwair() ) позволяет установить таймаут. По окончании этого периода ожидающий поток может быть разблокирован.

Барьеры

Барьер - это механизм синхронизации, который позволяет скоординировать работу нескольких взаимодействующих потоков таким образом, чтобы каждый из них остановился в заданной точке в ожидании остальных потоков, прежде чем продолжить свою работу.

В отличие от функции pthreadjoin() , при которой поток ожидает завершения другого потока, барьер заставляет потоки встретиться в определенной точке. После того как заданное количество потоков достигает установленного барьера, все эти потоки разблокируются и продолжат свою работу. Барьер создается с помощью функции pthread_barrier_init():

#include

pthread_barrier_init (pthread_barrier_t *barrier, const pthread_barrierattr_t *attr, unsigned int count);

В результате выполнения этого кода создается барьер по заданному адресу (указатель на барьер находится в аргументе barrier) и с атрибутами, установ­ленными аргументом attr. Аргумент count задает количество потоков, кото­рые должны вызвать функцию pthread_barrier_wait().

После создания барьера каждый поток вызывает функцию pthread_barrier_wait (), тем самым сообщая о завершения этого действия:

#include

int pthread_barrier_wait (pthread_barrier_t "barrier};

Когда поток вызывает функцию pthread_barrier_wait(), он блокируется до тех пор, пока то число потоков, которое было задано функцией pthread_barrier_init() , не вызовет функцию pthread_jbarrier_wait() и, соответст­венно, не заблокируется. После того как заданное количество потоков вы­зовет функцию pthread_barrier_wait() , все они разблокируются одновременно .

#include

#include

#include

#include

pthread_barrier_t barrier; // объект синхронизации типа "барьер"

main () // игнорировать аргументы

time_t now;// создать барьер со значением счетчика 3

pthread_barrier_init (&barrier, NULL, 3); // стартовать два потока - threadl и thread2

pthread_create (NOLL, NOLL, threadl, NULL); // потоки threadl и thread2 выполняются

pthread_create (NDLL, NDLL, thread2, NDLL);// ожидание завершения

printf ("main() waiting for barrier at %s", ctime (&now));

pthread_barrier_wait (&barrier);// после этого момента все три потока завершены

printf ("barrier in mainO done at %s", ctime (&now));

threadl (void *not used)

time (&now); // выполнение вычислений

printf ("threadl starting at %s", ctime (&now));// пауза

pthread_barrier_wait (&barrier) ;// после этого момента все три потока завершены

printf ("barrier in threadl{) done at %s", ctime (&now)) ;

thread2 (void *not__used)

time (&now) ; // выполнение вычислений

printf ("thread2 starting at %s", ctime (&now));// пауза

pthread_barrier_wait (&barrier) ;

// после этого момента все три потока завершены

printf {"barrier in thread2() done at %s", ctime (&now));

В примере из листинга основной поток создает барьер, после запуска которого начинается подсчет количества потоков, заблокированных на барьере для синхронизации. В данном случае количество синхронизируемых потоков задается равным 3: поток main(), поток thread1() и поток thread2().

Запускаются потоки thread1() и thread2(). Для наглядности в потоке задается пауза, чтобы имитировать процесс вычислений. Для выполнения синхрони­зации основной поток блокируется на барьере и ожидает разблокировки, которая произойдет после того, как остальные два потока не присоединятся к нему на этом барьере.



Ждущие блокировки

Ждущие блокировки (sleepon locks) работают аналогично условным пере­менным, за исключением некоторых деталей. Как и условные переменные, ждущие блокировки (pthread_sleepon_lock() ) могут использоваться для бло­кировки потока до тех пор, пока условие не станет истинным (аналогично изменению значения ячейки памяти). Но в отличие от условных перемен­ных (которые должны существовать для каждого проверяемого условия), ждущие блокировки применяются к одному мm.тексу и динамически созда­ваемой условной переменной независимо от количества проверяемых усло­вий. Максимальное число условных переменных в конечном итоге равно максимальному числу блокированных потоков.

Лучшие статьи по теме