Генератор Python: динамическая регулировка скорости конвейера

Напишите решение на Python и проверьте его на странице.

Другие упражнения по этой теме: Генератор send в Python: задачи на состояние и управление потоком.

Регулятор скорости конвейера

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

Каждую минуту регулятор принимает целое число прибывших коробок и сопоставляет его с окном нормы от 10 до 20 штук включительно. Если коробок больше нормы, скорость конвейера увеличивается на действующий шаг подстройки, а если меньше — снижается на этот же шаг, но никогда не опускается ниже нуля. Когда поток укладывается в границы нормы, скорость остаётся прежней. В ответ на каждое показание сопрограмма возвращает новое зафиксированное значение скорости.

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

Определите, как будет меняться скорость конвейерной ленты при поступлении всей последовательности показаний датчика и калибровочных команд.

Что уже дано

В редакторе представлена заготовка генераторной функции speed_controller(initial_speed, step). Вспомогательные функции наблюдения доступны при проверке, реализовывать их заново не требуется.

Что нужно сделать

Реализуйте функцию-генератор speed_controller(initial_speed, step).

Функция принимает два числовых аргумента:

  • initial_speed — начальная скорость конвейера (неотрицательное конечное число int или float, включая их подклассы, от 0 до 1 000 000);
  • step — начальный шаг изменения скорости (неотрицательное конечное число int или float, включая их подклассы, от 0 до 1 000 000).

Функция возвращает нативный неинициализированный генератор (сопрограмму), сохраняющий текущую скорость кумулятивно. При вызове функции прайминг производиться не должен — первый запуск выполняется вызывающей стороной.

Правила работы генератора:

  • Первый вызов next() или .send(None) выполняет инициализацию (прайминг) и должен вернуть None.
  • После прайминга генератор принимает сообщения двух типов (до 1000 сообщений за сессию):
  1. Неотрицательное целое число boxes (от 0 до 1 000 000, включая подклассы int) — количество прибывших коробок. Если 10 <= boxes <= 20, текущая скорость остаётся без изменений. Если boxes > 20, текущая скорость увеличивается на текущий step. Если boxes < 10, текущая скорость уменьшается на текущий step, но не может стать меньше 0 (значение снизу ограничено нулём). В ответ генератор возвращает обновлённую текущую скорость.
  2. Калибровочный кортеж вида ("step", new_step), где new_step — новое значение шага подстройки с теми же числовыми границами, что и у начального шага. При получении калибровки обновляется только величина шага step, текущая скорость остаётся неизменной, а генератор возвращает это текущее сохранённое значение скорости.
  • Возвращаемая скорость должна быть числовым значением (int или float), без дополнительного округления или искажения.
  • Генератор должен корректно поддерживать стандартные механизмы завершения и обработки ошибок (.close() и .throw()).
  • Каждый созданный экземпляр регулятора работает независимо от остальных.

Ввод и вывод

Стандартные потоки ввода stdin и вывода stdout в решении не используются: считывать ввод и вызывать print() не нужно. После выполнения кода учащегося проверяющая система считывает из пространства имён модуля функцию верхнего уровня speed_controller и вызывает её с проверочными аргументами.

Пример использования

g=speed_controller(3,2)
print(next(g))
print(g.send(21))
print(g.send(('step', .5)))
print(g.send(9))
print(g.send(10))
g.close()

Вывод:

None
5
5
4.5
4.5
РешениеPython

Без регистрации. Гостевая проверка не сохраняет прогресс. Для сохранения перейдите к уроку.

Отправьте решение, чтобы увидеть результаты тестов.

Связанные задачи