Page 116 - 6571
P. 116
буфера. На початковому етапі припустимо, що існує тільки один
виробник та споживач. Виробник розміщує повідомлення в
спільному буфері, а споживач витягує їх звідти. Буфер містить
чергу вже поміщених, але ще не витягнутих повідомлень. Така
черга може бути представлена зв’язаним списком або масивом.
Отже, нехай буфер буде масивом buf[n], де n > 1. Нехай
змінна front – індекс першого повідомлення черги, a rear –
індекс першої порожньої комірки після повідомлення в кінці
черги. Спочатку змінні front та rear мають однакові значення,
наприклад, 0.
При такому представленні буфера виробник поміщає в нього
повідомлення із значенням data, виконуючи для цього наступні
дії:
buf[rear] = data;
rear = (rear+1) % n;
Аналогічно споживач витягує повідомлення в свою локальну
змінну result, виконуючи дії:
result = buf[front];
front = (front+1) % n;
Оператор взяття залишку (%) використовується для того щоб
значення змінних front та rear завжди були в межах від 0 до
n-1. Черга буферизованих повідомлень зберігається в комірках
включно від buf[front] до buf[rear] (не включно). Змінна
buf інтерпретується як кільцевий масив, в якому за значенням
buf[n-1] слідує значення buf[0]. Ось приклад конфігурації
масиву buf, де затемнені комірки заповнені, а білі – вільні
(рис. 13.1).
Рисунок 13.1 – Конфігурація масиву buf
Якщо використовується тільки один буфер (як у задачі
«виробник-споживач»), то виконання операцій deposit та fetch
має чергуватися. За наявності декількох буферів операцію
deposit можна виконати, якщо існує порожня клітинка, a fetch
115