ТЗ на разработку Система планирования и диспетчеризации поставок товарного бетона «CementFlow» (Предварительная версия)
1. ВВЕДЕНИЕ
1.1. Наименование проекта
Система планирования и диспетчеризации поставок товарного бетона «CementFlow» с поддержкой каскадного перерасчёта.
1.2. Краткое описание
Разрабатываемая система предназначена для оптимального распределения грузовиков-миксеров для выполнения заказов на доставку товарного бетона в течение 12-часовой рабочей смены. Система обеспечивает автоматическое планирование поставок, мониторинг исполнения в реальном времени и интеллектуальный перерасчёт расписания при возникновении сбоев (поломки техники, ДТП, задержки).
Система использует гибридную слотовую модель планирования: визуальный интерфейс диспетчера представляет расписание в виде сетки фиксированных временных интервалов (слотов) для удобства восприятия и ручного управления, в то время как ядро системы работает с непрерывной временной шкалой для точных вычислений.
Система предназначена для работы с несколькими производственными базами (ЦБЗ). Автоматическое распределение заказов между ними осуществляется по взвешенному географическому принципу, который учитывает не только расстояние до объекта клиента, но и текущую загрузку каждой базы для балансировки производственной мощности.
Водитель является активным участником системы через мобильное приложение, получает задания (поставки) и имеет возможность отклонять назначенную ему поставку, что немедленно инициирует процедуру перепланирования данного рейса и связанных с ним задач.
1.3. Область применения
Система предназначена для использования:
-
Бетонными заводами и производственными комплексами
-
Логистическими компаниями, специализирующимися на перевозке строительных материалов
-
Диспетчерскими службами строительных компаний
1.4. Цели разработки
-
Повышение эффективности использования парка машин на 25-30%
-
Снижение простоев грузовиков-миксеров на 35-40%
-
Минимизация потерь бетона из-за превышения времени жизни
-
Обеспечение 95% своевременности доставок
-
Сокращение времени реакции на сбои с 30-60 минут до 5-10 минут
2. ОБЩИЕ ТРЕБОВАНИЯ
2.1. Функциональное назначение
Система должна обеспечивать:
2.1.1. Основные функции:
-
Планирование смены - формирование оптимального расписания поставок (слотов) на 12-часовую смену с распределением заказов между несколькими ЦБЗ.
-
Распределение техники - автоматический подбор грузовиков-миксеров (АБС) и автобетононасосов (АБН) для выполнения поставок с учётом их синхронизации.
-
Мониторинг исполнения - отслеживание статуса поставок и местоположения техники в реальном времени.
-
Полуавтоматический каскадный перерасчёт - интеллектуальное перепланирование при возникновении сбоев с генерацией вариантов и обязательным утверждением изменений диспетчером.
-
Визуализация - отображение расписания в виде интерактивной диаграммы Ганта и на карте.
2.1.2. Вспомогательные функции:
-
Управление справочниками (машины, водители, клиенты, объекты)
-
Формирование отчётности и аналитика
-
Интеграция с внешними системами (GPS, ERP, CRM)
-
Уведомления и оповещения
2.2. Пользователи системы
| Роль пользователя | Основные функции | Доступ |
|---|---|---|
| Диспетчер | Полный доступ ко всем функциям планирования и мониторинга | Веб-интерфейс |
| Руководитель смены | Просмотр, утверждение расписания, анализ эффективности | Веб-интерфейс |
| Водитель | Получение заданий, отметка о выполнении этапов, отклонение заказа с указанием причины, сообщение о проблемах | Мобильное приложение |
| Администратор | Управление пользователями, настройка системы, техническая поддержка | Веб-интерфейс |
| Клиент (опционально) | Просмотр статуса своего заказа, получение уведомлений | Веб-портал/SMS |
3. ТЕХНОЛОГИЧЕСКИЕ ТРЕБОВАНИЯ
3.1. Архитектурные требования
-
Микросервисная архитектура с разделением на независимые модули
-
Событийно-ориентированная архитектура для обработки событий в реальном времени
-
REST API для интеграции с внешними системами
-
Веб-сокеты для обновления интерфейса в реальном времени
-
Поддержка горизонтального масштабирования
3.2. Технологический стек
| Компонент | Технологии |
|---|---|
| Бэкенд | .NET 8, C# 12, ASP.NET Core |
| Фронтенд | React 18 + TypeScript, Redux Toolkit/ Svelte SvelteKit + TypeScript |
| База данных | PostgreSQL 16 (основная), Redis 7 (кэш) |
| Очереди сообщений | RabbitMQ |
| Контейнеризация | Docker, Docker Compose |
| Оркестрация | Kubernetes (опционально) |
| Мониторинг | Grafana, Prometheus |
| CI/CD | GitLab CI/CD или GitHub Actions |
3.3. Требования к производительности
| Параметр | Требование |
|---|---|
| Время отклика API | ≤ 200 мс для 95% запросов |
| Время планирования смены | ≤ 30 секунд для 100 заказов |
| Время каскадного перерасчёта | ≤ 10 секунд |
| Поддержка одновременных пользователей | ≥ 50 диспетчеров |
| Доступность системы | 99.5% (SLA) |
| Время восстановления | ≤ 15 минут |
4. ДЕТАЛЬНОЕ ОПИСАНИЕ ФУНКЦИОНАЛА
4.1. Модуль управления заказами
4.1.1. Создание и редактирование заказов
-
Форма создания заказа с полями:
-
Клиент (выбор из справочника)
-
Объект доставки (адрес, контактное лицо, телефон)
-
Объём бетона (м³)
-
Марка бетона, подвижность
-
Желаемое время доставки (окно или точное время)
-
Приоритет (нормальный, высокий, критический)
-
Особые требования (непрерывная заливка, бетононасос и т.д.)
-
Предмет заливки (выбор из справочника) - влияет на нормативное время разгрузки.
-
Требуется автобетононасос (АБН) (флажок Да/Нет).
-
Приоритет клиента (выбор: нормальный, высокий, критический) - определяет допустимый интервал доставки (например, ±30 мин, ±60 мин, ±120 мин).
-
4.1.2. Автоматическое разбиение заказов на поставки
-
Алгоритм разбиения учитывает:
-
Вместимость доступных машин
-
Требование непрерывной заливки
-
Оптимальное заполнение миксера (минимизация остатков)
-
4.1.3. Управление сменами и доменными сущностями
Система оперирует следующими ключевыми бизнес-сущностями, которые необходимо учитывать при планировании и диспетчеризации:
-
Смена (Shift): Центральный агрегат, объединяющий все данные на рабочий день (12 часов). Атрибуты: уникальный ID, дата, время начала и окончания, статус (в планировании, активна, завершена, отменена). Смена является контейнером для заказов, поставок, назначений машин и слотов расписания.
-
Слот (ScheduleSlot): Базовый элемент планирования. Представляет собой временной интервал, выделенный конкретной машине (АБС/АБН) для выполнения конкретной задачи. Атрибуты: уникальный ID, время начала, время окончания, статус (свободен, забронирован, в процессе, выполнен, отменен), привязка к машине (Truck/ConcretePump), привязка к поставке (Delivery), привязка к смене (Shift).
-
Производственная база (ЦБЗ) (ProductionBase): Объект производства и отправки продукции. Атрибуты: уникальный ID, название, юридический и фактический адрес, геокоординаты, статус (активна, на обслуживании), привязка к графику работы (PlantSchedule). Влияет на распределение заказов.
-
График работы завода (PlantSchedule): Расписание доступности производственной базы. Атрибуты: уникальный ID, привязка к ProductionBase, день недели, время начала и окончания рабочего дня, перерывы (опционально). Определяет временные окна для погрузки.
-
Событие (Event): Запись о любом значимом отклонении от плана или изменении статуса. Атрибуты: уникальный ID, тип (поломка, ДТП, задержка, отклонение водителем, изменение статуса ТС и т.д.), дата и время возникновения, источник (система, диспетчер, водитель), описание, критичность, привязка к связанным сущностям (машина, поставка, слот). Является триггером для алгоритмов перерасчета и основой для аналитики.
4.2. Модуль планирования
4.2.1. Алгоритм первоначального распределения
Детальное описание приведено в Приложении №1.
Входные данные:
-
Список всех заказов смены
-
Парк доступных машин с характеристиками
-
Расписание работы завода
-
Список производственных баз (ЦБЗ) с координатами и графиком работы.
-
Список автобетононасосов (АБН) с характеристиками, статусом и привязкой к ЦБЗ.
-
Глобальные настройки: временной буфер между заказами (% или минуты), минимальный процент загрузки миксера.
-
Активная смена (Shift) на дату планирования, к которой будут привязаны все создаваемые сущности (поставки, слоты).
-
График работы (PlantSchedule) для каждой производственной базы (ЦБЗ), участвующей в планировании. Алгоритм должен учитывать только те временные окна, когда завод доступен для погрузки.
Этапы алгоритма:
-
Группировка заказов по приоритету и временным окнам
- Привязка заказов к ЦБЗ и проверка графика: при выборе ЦБЗ для заказа система должна проверить, что желаемое время доставки клиента может быть обеспечено с учетом графика работы выбранного завода. Если нет — необходимо предложить альтернативные слоты или ЦБЗ.
- производственной базой на основе минимального расстояния до объекта и текущей загрузки базы.
-
Разбиение на поставки с учётом непрерывности заливки
-
Распределение по машинам по критериям:
-
Минимизация порожнего пробега
-
Максимальное использование вместимости
-
Учёт приоритета клиента
-
При подборе ТС проверяется соответствие минимальному проценту загрузки.
-
Для заказов с АБН осуществляется парный подбор: поиск свободного слота для АБС и синхронизированного по времени слота для подходящего АБН с учётом его времени переезда.
-
-
Расчёт временных окон с учётом:
-
Времени жизни бетона (90-120 минут)
-
Времени на погрузку, путь, разгрузку, возврат
-
Буфера на форс-мажор (10-15%)
-
-
Формирование диаграммы Ганта - визуализирует распределение слотов (ScheduleSlot), принадлежащих конкретной смене (Shift), по машинам (АБС/АБН) на временной шкале.
4.2.2. Критерии выбора машины
Формула оценки приоритета машины:
Score = (W1 × DistanceScore) + (W2 × CapacityUtilization) + (W3 × TimeWindowFit) + PriorityBonus
где:
-
DistanceScore - оценка расстояния до завода (ближе = лучше)
-
CapacityUtilization - коэффициент заполнения миксера
-
TimeWindowFit - соответствие временному окну клиента
-
PriorityBonus - бонус за приоритет клиента
-
W1, W2, W3 - весовые коэффициенты (настраиваемые)
4.3. Модуль каскадного перерасчёта
4.3.1. Типы обрабатываемых событий
Все перечисленные события (поломка, ДТП, задержка, отклонение водителем и пр.) фиксируются в системе как сущности Event. Каждое событие имеет тип, временную метку, источник и привязку к затронутой сущности (машина, поставка, слот).
-
Поломка машины - машина выходит из строя
-
ДТП - авария с участием машины
-
Задержка на разгрузке - превышение планового времени разгрузки
-
Пробки - увеличение времени в пути
-
Изменение заказа - корректировка клиентом
-
Новая доступная машина - ввод машины в эксплуатацию
- Отклонение заказа водителем - водитель отказался от выполнения через мобильное
- Изменение статуса машины "На линии" - ручное снятие машины с эксплуатации.
4.3.2. Алгоритм перерасчёта
Алгоритм является полуавтоматическим (автоматическим расчет с ручным утверждением рассчитанного сценария диспетчером). Система анализирует воздействие, генерирует варианты перепланирования, но не применяет их автоматически. Окончательное решение и утверждение изменённого расписания остаётся за диспетчером.
Детально приведен в Приложении №2.
Алгоритм Шагктивируется 1:в Анрежиме реализьного воздействия и изоляция
Определмение всех затронутыхпоставок.Перевод затронутых поставок в статус "На перепланировании"и освобождение занятых ими слотов.На основепоступленившегоиСсобытия сбоя (Event)TruckStatusChanged,сDeliveryDelayReported,TruckBreakdown) истемали опртклонеделяетнии заказа водителем.А. Принцип Двухуро
нутыеСлоты (ScheduleSlot)иПоставки (Deliveries)в рамках текущей активневойСмРены (Shift).
Шаг 2: Генеракция вариантов и уведомление
-
Система
формируазделяет сбои на две категории, чтобы обеспечить достижение целевого времени реакции ($\le 10$ секунд) для некритических случаев.-
Tier 1: Автоматическая Коррекция (Мягкое Каскадирование)
-
Триггер: Задержка текущего слота (или начало следующего) меньше, чем
Форс-мажорный_буфер(T_buffer), и сдвиг не нарушает Критическое Ограничение (Время жизни бетона или SLA клиента). -
Действие: Система автоматически сдвигает посл
ько вариантов новогоедующее расписанияес миниматольными нарушениями. Диспетчер получаетвизуальное уведомлениес подсветкойзатронутыхого ТС, поглощая задержказоу в буфере.-
Результат: Перерасчёт завершён за $\le 10$ секунд, без участия диспетчера.
-
-
Tier 2: Полуавтоматический Кризис (Жесткое Каскадирование)
-
Триггер: Поломка ТС, ДТП, задержка превышает
Форс-мажорный_буфер, или сдвиг нарушает Критическое ОграммничениеГаили SLA клиента.
-
-
ШДействие: Система генерирует3:иУпредставляет диспетчеру 3 лучших варианта решения. -
Результат: Требуется ручное утверждение диспетчером.
-
Б. Этапы Обработки Сбоя
1. Изоляция Сбоя и Расчёт Задержки ($\Delta t$)
-
Определение $\Delta t$: Фиксация фактического времени задержки или оценка минимального времени простоя при поломке.
-
Изоляция: Затронутый слот (и все последующие слоты данной машины) блокируются.
-
Критическое Ограничение: Проверка первого затронутого слота:
Новое_Время_Разгрузки$\le$Время_начала_погрузки+Время_жизни_бетона.-
ДЕсли ограничение нарушено, дальнейшие действия немедленно переводятся на Tier 2, независимо от размера буфера.
-
2. Решение Tier 1: Автоматическая Коррекция
-
Условие: $\Delta t \le$
Slot.BufferTimeИКритическое Ограничениесоблюдено. -
Действие:
-
Для первого последующего слот
ча ($S_n$): $S_n.\text{Start} = S_{n-1}.\text{End} + \Delta t$ -
Рекурсивно применить сдвиг $\Delta t$ ко всем последующим слотам данного ТС.
-
Стат
риваетус:предложенные варианты, может вручную с«Скорректироватьн».их (например, перетащив слот) или запросить другие варианты. Только после явного утУверждомленияе диспетчеромуизмененвыводия фиксируютсяв общем расписании.
-
Шаг3.
4: ИнформироваРешение стTier 2: Порон
Системалуавтоматический Кризис-
Условие: $\Delta t >$
Slot.BufferTimeИЛИ нарушениеКритического ОграниченияИЛИ поломка ТС. -
Действие:
-
Потерянный Слот: Все затронутые, но не начатые поставки (слоты) возвращаются в пул с наивысшим приоритетом (Critical).
-
Генерация Вариантов:
-
Алгоритм распределения (4.2.1) ищет от 3 до 5 лучших альтернативных слотов (на других ТС или на более поздних окнах для этого же ТС).
-
Критерии поиска:
-
Приоритет 1 (Абсолютный): Спасти поставки с нарушением
Критического Ограничения(Время жизни бетона). -
Приоритет 2 (Взвешенный): Минимизировать нарушение SLA для всех последующих затронутых поставок (общий сдвиг).
-
Приоритет 3 (Взвешенный): Минимизировать порожний пробег нового ТС.
-
-
-
Эскалация: Диспетчеру немедленно выдается Критическое Уведомление с представлением вариантов и их последствиями (например, «Вариант 1: Слот A переходит на Т05, но Слот B будет заде
йржан на 45 минут»). -
Статус: «Ожидает утверждения». Система ожидает ручного выбора вариан
ныхтаводиспетелей и, при необходимости, менеджчеров для информирования клиентов.
-
4.4. Модуль визуализации
4.4.1. Диаграмма Ганта
Требования к отображению:
-
По горизонтали - временная шкала смены (12 часов)
-
По вертикали - список машин
-
Для каждой машины - цветные блоки поставок
-
Цветовая индикация статуса:
-
Зелёный - выполняется по плану
-
Жёлтый - есть риски/небольшие отклонения
-
Красный - критические отклонения/просрочки
-
Серый - завершено
-
Интерактивные возможности:
-
Drag-and-drop для ручного перемещения поставок
-
Масштабирование (часы/минуты)
-
Фильтрация по клиентам, объектам, статусам
-
Подсказки при наведении (детали поставки)
4.4.2. Карта перемещений
-
Отображение местоположения машин в реальном времени
-
Маршруты движения
-
Точки погрузки и разгрузки
-
Пробки и дорожная обстановка (интеграция с картами)
4.5. Модуль интеграций
4.5.1. Внешние системы
Система Тип интеграции Назначение GPS/телематика REST API/WebSocket Отслеживание местоположения, статуса машин Картографические сервисы API (Яндекс.Карты/Google Maps) Расчёт маршрутов и времени в пути с учётом актуальных пробок. 1C:ERP REST API Получение финансовых данных: цена заказа, финансовое состояние клиента, стоимость продукта. CRM система REST API Получение информации о клиентах СМС-сервис REST API Уведомления водителей и клиентов Погодный сервис REST API Учёт погодных условий в планировании 5. ТРЕБОВАНИЯ К ДАННЫМ
5.1. Структура базы данных
5.1.1. Основные таблицы:
-
Shifts - Смены. Атрибуты: id, date, start_time, end_time, status, created_at.
-
Orders - заказы клиентов. Атрибуты: id, shift_id, client_id, construction_site_id, ...
-
Deliveries - поставки (части заказов). Атрибуты: id, order_id, truck_id, ...
-
Trucks - грузовики-миксеры (АБС). Атрибуты: id, production_base_id, license_plate, capacity, status, ...
-
Drivers - водители.
-
Clients - клиенты.
-
ConstructionSites - объекты строительства.
-
ScheduleSlots - слоты в расписании. Атрибуты: id, shift_id, truck_id (или concrete_pump_id), delivery_id, start_time, end_time, status, type (for АБС/АБН).
-
Events - события системы. Атрибуты: id, type, severity, source, description, related_entity_type (truck, delivery, slot), related_entity_id, occurred_at, resolved_at.
-
RoutePoints - точки маршрутов.
-
ConcretePumps - автобетононасосы (АБН). Атрибуты: id, production_base_id, type, status, ...
-
ProductionBases - производственные базы (ЦБЗ). Атрибуты: id, name, address, coordinates, status.
-
PlantSchedules - графики работы заводов. Атрибуты: id, production_base_id, day_of_week, start_time, end_time, is_active.
-
PouringItems - предметы заливки.
-
TruckOnDutyStatus - история статусов ТС "На линии".
5.1.2. Требования к хранению:
-
История изменений расписания - 90 дней
-
Архив выполненных поставок - 3 года
-
Логи событий - 30 дней
-
Оперативные данные - в кэше Redis
5.2. Форматы данных
5.2.1. JSON API форматы:
{ "order": { "id": "ORD-2024-001", "client": { "id": "CL-001", "name": "ООО СтройГрад", "priority": "high" }, "site": { "address": "ул. Строителей, 15", "coordinates": {"lat": 55.7558, "lng": 37.6176} }, "details": { "volume": 15.0, "concreteGrade": "M300", "slump": 15, "pouringItem": "Фундамент", "concretePumpRequired": true, "clientPriority": "high", "allowedDeliveryIntervalMinutes": 60, "requiredWindow": { "start": "2024-01-15T09:00:00", "end": "2024-01-15T12:00:00" }, "continuousPouring": true, "maxInterval": "PT30M" } } }5.3. Аспекты требующие дальнейшего уточнения и проработки в рамках бизнес-процесса
-
Игнорирование времени жизни бетона при планировании:
-
Предполагается, что время жизни бетона — 90–120 минут, но нет механизма контроля этого параметра при каскадном перерасчете.
-
Отсутствует логика автоматического исключения поставок, нарушающих этот порог.
Признанный Недостаток Требуемое Алгоритмическое Решение Игнорирование времени жизни бетона при каскадном перерасчете
Hard Constraint (Жесткое Ограничение): В алгоритме перерасчета (4.3.2) должно быть введено правило: если новое рассчитанное время разгрузки превышает Время_начала_погрузки + Время_жизни_бетона (120 минут), слот автоматически исключается из вариантов перепланирования.Неполный учет непрерывной заливки
Связанный Штраф (Coupled Penalty): В оценочную функцию (
Score) необходимо добавить весовой коэффициент W5 \times ContinuousPouringPenalty. Штраф должен экспоненциально расти, если рассчитанный интервал между последовательными поставками Δt превышаетМаксимальный_интервал (например, 30 минут).
-
-
Неполный учет непрерывной заливки:
-
Указано, что заказы могут требовать непрерывной заливки, но нет описания алгоритма, обеспечивающего гарантированное соблюдение интервалов между поставками.
-
Не указано, как система будет реагировать на сбой одной из поставок в цепочке непрерывной заливки.
-
-
Недостаточная детализация маршрутов:
-
Отсутствует учет обратного маршрута машины при планировании следующей поставки.
-
Не учитываются реальные ограничения по дорогам, пробкам, погоде, что критично для точности расчета слотов.
-
-
Неполная модель взаимодействия с водителем:
-
Водитель может отклонить заказ, что инициирует перерасчет, но нет описания, как система гарантирует, что перерасчет не приведет к нарушению непрерывной заливки или времени жизни бетона.
-
-
Неопределенность в синхронизации АБС и АБН:
-
Указано, что требуется синхронизация автобетоносмесителя и автобетононасоса, но нет алгоритма или модели, обеспечивающей согласованность их слотов. Синхронизация АБС и АБН (Автобетононасосы): В настоящее время требование парного подбора не отражено в оценочной функции
-
-
Проблема: В оценочной функции для АБС отсутствует фактор доступности АБН.
-
Решение:
-
Создание Сдвоенного Слота: При планировании заказа с АБН, система должна формировать два связанных слота (
ScheduleSlot) в базе данных: один для АБС, другой для АБН -
Проверка Временного Окна АБН: Слот АБС (время разгрузки) должен быть полностью вложен во временное окно АБН (время установки + время работы + время демонтажа).
-
Штраф за Несоответствие: В оценочную функцию АБС добавить жесткий запрет или бесконечный штраф, если требуемый АБН недоступен в нужное время.
-
-
-
-
Не описано, как система будет действовать при недоступности АБН.
-
-
Неполная модель статуса машины "На линии":
-
Указано, что статус может меняться вручную, но не описано, как это влияет на уже запланированные поставки.
-
Нет механизма блокировки назначения машины, если она снята с линии.
-
-
Нет алгоритма синхронизации АБС и АБН:
-
Требуется описание, как система подбирает парные слоты для техники с учетом времени переезда и доступности.
-
-
Нет алгоритма оценки риска при перерасчете:
-
Требуется описание, как система определяет, какие поставки находятся "под риском" при сбое.
-
-
Нет механизма ограничения глубины каскадного перерасчета:
-
Отсутствует логика, предотвращающая лавинообразный сдвиг расписания.
Признанный Недостаток Необходимая Логика в Алгоритме (4.3.2) Нет алгоритма выбора ЦБЗ при перерасчете
При генерации вариантов для потерянного слота система должна автоматически включать ЦБЗ других баз в пул кандидатов, если это минимизирует общую задержку или спасает критический заказ, даже если первоначально заказ был привязан к другой базе. Нет механизма ограничения глубины каскадного перерасчета
Ввести Лимит Сдвига (Shift Limit): Если перераспределение слота сдвигает его на время, превышающее заданный предел (например, 60 минут от оригинального времени), алгоритм должен остановить дальнейший каскад для этой ветки и представить сдвиг диспетчеру как конфликт. Нет алгоритма оценки риска
Ввести Метрику Риска: При перерасчете каждый затронутый слот должен получать Рейтинг Риска (Risk Score), основанный на: 1) Критической близости к лимиту жизни бетона и 2) Близости к нарушению SLA клиента. Варианты перерасчета, минимизирующие этот общий риск-скор, должны быть приоритетными для утверждения.
-
-
Нет алгоритма выбора ЦБЗ при перерасчете:
-
При изменении заказа или сбое не описано, может ли заказ быть переназначен на другую базу.
-
Нет логики отмены поставки:
Требуется описание, как система отменяет поставку, если она становится невозможной (например, из-за недоступности машины).
- Введение Двухуровневой Системы Реагирования
Категория Триггер Допустимое Действие Время Реакции Уровень 1: Некритический Сдвиг (Автоматический) Задержка на предыдущем слоте < Буферного времени текущего слота (например, задержка 10 мин при буфере 15 мин). Автоматический сдвиг всего последующего расписания данной машины. Все сдвиги остаются в пределах временных окон (SLA) клиентов. <= 10 секунд (выполняется алгоритмом) Уровень 2: Критический Сбой (Полуавтоматический) Поломка ТС, ДТП, задержка > Буферного времени, сдвиг выводит слот за SLA клиента, или требуется переназначение слота на другую машину. Алгоритм генерирует 3 лучших варианта (переназначить, отменить, сдвинуть с нарушением SLA) и ожидает подтверждения диспетчера. <= 10 секунд (генерация вариантов) + Ручное утверждение (3–5 минут) 5.3. Риски и рекомендации
-
Риск нарушения SLA* при непрерывной заливке:
-
Без строгого контроля интервалов между поставками и времени жизни бетона возможны массовые нарушения.
-
-
Риск перегрузки диспетчера при полуавтоматическом перерасчете:
-
При большом количестве событий диспетчер может не успевать утверждать изменения вручную.
-
-
Риск неконсистентности данных при ручной смене статуса машины:
-
Без блокировок и проверок возможны конфликты между статусом машины и назначенными слотами.
-
-
Риск неэффективного использования АБН:
-
Без модели синхронизации и маршрутизации насосы могут простаивать или опаздывать.
-
* - соглашение об уровне обслуживания (Service Level Agreement), формальный договор между заказчиком и поставщиком услуг, определяющий параметры качества, такие как доступность сервиса, время реакции на проблемы и восстановления. В контексте вашего текста о рисках в заливке бетона и работе с АБН (автобетононасосами), нарушение SLA подразумевает несоблюдение гарантированных сроков поставок или времени жизни материалов, что приводит к массовым сбоям.
6. ТРЕБОВАНИЯ К ИНТЕРФЕЙСУ
6.1. Веб-интерфейс диспетчера
6.1.1. Основной экран:
-
Левая панель - список заказов с фильтрами
-
Центральная область - диаграмма Ганта
-
Правая панель - детали выбранного элемента, уведомления
-
Верхняя панель - управление сменой, поиск, настройки
- На диаграмме Ганта слоты (блоки поставок) отображаются в рамках сетки временных интервалов. Доступна панель управления списком ТС "На линии" с возможностью быстрого включения/выключения.
6.1.2. Экран планирования:
-
Календарь смен
-
Форма массового планирования
-
Инструменты оптимизации
-
Предпросмотр нагрузки на завод
6.1.3. Экран мониторинга:
-
Карта с движением машин
-
Панель статусов в реальном времени
-
Графики загрузки и эффективности
-
Оповещения о проблемах
6.2. Мобильное приложение водителя
6.2.1. Основные экраны:
-
Задания на день - список поставок
-
Текущее задание - детали, карта маршрута, при наличии – отображается информация о необходимом автобетононасосе (АБН) и времени его работы.
-
Отметки о выполнении - кнопки для отметки этапов
-
Сообщения - связь с диспетчером
-
Проблемы - форма сообщения о сбоях
6.2.2. Функционал:
-
Авторизация по QR-коду или логину
-
Офлайн-работа с последующей синхронизацией
-
GPS-трекинг
-
Фотоотчётность (по требованию)
6.2.3. Отклонение заказа:
Водитель имеет кнопку для отклонения текущего/назначенного задания с обязательным указанием причины из списка (болезнь, поломка ТС и т.д.). Отклонение передаётся в систему и инициирует процедуру перерасчёта.
7. ТРЕБОВАНИЯ К НАДЁЖНОСТИ И БЕЗОПАСНОСТИ
7.1. Надёжность
-
Резервирование всех критических компонентов
-
Автоматическое восстановление после сбоев
-
Ежедневное резервное копирование с хранением 7 дней
-
Мониторинг доступности и производительности
7.2. Безопасность
-
Аутентификация по логину/паролю + 2FA для администраторов
-
Ролевая модель доступа (RBAC)
-
HTTPS для всех соединений
-
Защита от DDoS атак
-
Аудит действий пользователей
-
Шифрование конфиденциальных данных
8. ТРЕБОВАНИЯ К РАЗВЁРТЫВАНИЮ И ЭКСПЛУАТАЦИИ
8.1. Развёртывание
-
Контейнерная поставка всех компонентов
-
Автоматическое развёртывание через CI/CD
-
Документация по установке и настройке
-
Миграционные скрипты для обновлений
8.2. Эксплуатация
-
Техническая поддержка 24/7 для критических инцидентов
-
Обновления - 1 раз в месяц (патчи), 1 раз в квартал (версии)
-
Мониторинг - дашборды, алертинг, логирование
-
Резервное копирование - автоматическое, ежедневно
9. ЭТАПЫ РАЗРАБОТКИ
Этап 1: Прототип и архитектура (1-2 месяца)
-
Разработка архитектуры
-
Создание прототипа алгоритмов планирования
-
Проектирование БД и API
-
Базовый веб-интерфейс
Этап 2: Ядро системы (3-4 месяца)
-
Реализация основных модулей
-
Алгоритмы распределения и перерасчёта
-
Веб-интерфейс диспетчера
-
Интеграция с GPS/картами
Этап 3: Доработка и тестирование (2-3 месяца)
-
Мобильное приложение для водителей
-
Расширенная аналитика
-
Стресс-тестирование
-
Пилотная эксплуатация
Этап 4: Внедрение и поддержка (постоянно)
-
Внедрение у заказчика
-
Обучение пользователей
-
Техническая поддержка
-
Доработки по обратной связи
10. КРИТЕРИИ ПРИЁМКИ
10.1. Функциональные критерии
-
Система корректно планирует смену для 100+ заказов
-
Автоматический перерасчёт выполняется за ≤10 секунд
-
Диаграмма Ганта отображает все поставки без пересечений
-
Интеграция с GPS работает в реальном времени
-
Мобильное приложение работает офлайн
10.2. Нефункциональные критерии
-
Время отклика интерфейса ≤200 мс
-
Система выдерживает нагрузку 50+ одновременных пользователей
-
Доступность 99.5% в рабочее время
-
Данные сохраняются при перезапуске системы
10.3. Приёмочные испытания
-
Тестирование на тестовых данных - 7 дней
-
Пилотная эксплуатация - 14 дней
-
Стресс-тестирование - имитация сбоев и высокой нагрузки
-
Проверка безопасности - пентест
11. ГАРАНТИИ И ПОДДЕРЖКА
11.1. Гарантийный период
-
12 месяцев с момента подписания акта приёмки
-
Исправление критических багов - в течение 24 часов
-
Исправление некритических багов - в течение 5 рабочих дней
11.2. Техническая поддержка
-
Поддержка 24/7 для критических инцидентов
-
Консультации по использованию системы
-
Обновления и доработки по согласованию
-
Резервное копирование и восстановление данных
ПРИЛОЖЕНИЯ
Приложение A: Словарь терминов
-
Слот - временной интервал, выделенный машине для выполнения поставки
-
Каскадный перерасчёт - последовательное перепланирование зависимых поставок
-
Время жизни бетона - период от замеса до начала схватывания (90-120 минут)
-
Непрерывная заливка - требование минимального интервала между поставками на объект
Приложение B: Схемы интеграций
(Диаграммы последовательности и архитектурные схемы)
Приложение C: Макеты интерфейсов
(Визуальные макеты всех экранов системы)
ИСПОЛНИТЕЛЬ: [Наименование организации-исполнителя]
ЗАКАЗЧИК: [Наименование организации-заказчика]
СРОК РАЗРАБОТКИ: 8-12 месяцев
СТОИМОСТЬ РАЗРАБОТКИ: [Сумма] руб.
СРОК ДЕЙСТВИЯ ТЗ: до [Дата]
Документ утверждён:
[Подпись Заказчика] [Подпись Исполнителя]
[Дата] [Дата]
Приложение №1
ДЕТАЛЬНОЕ ОПИСАНИЕ АЛГОРИТМА ПЕРВОНАЧАЛЬНОГО РАСПРЕДЕЛЕНИЯ
1. ОБЩИЙ ПРИНЦИП РАБОТЫ АЛГОРИТМА
Алгоритм первоначального распределения — это многоуровневая жадная эвристика с обратной связью, которая преобразует список заказов клиентов в оптимизированное расписание поставок для всего парка машин на 12-часовую смену. Алгоритм работает по принципу "наиболее ограниченные задачи решаются первыми".
Ключевая идея: Сначала назначаются самые сложные и критичные поставки, затем менее сложные, что позволяет избежать ситуаций, когда критичные задачи невозможно выполнить из-за того, что все ресурсы уже заняты менее важными задачами.
2. ПОШАГОВЫЙ АЛГОРИТМ С РАСЧЁТАМИ
Этап 0: Подготовка данных (Pre-processing)
Входные данные:
-
Список заказов на смену (N заказов)
-
Парк доступных машин (M единиц)
-
Параметры смены (начало T_start, конец T_end, координаты завода)
-
Технологические константы (время погрузки, средняя скорость и т.д.)
-
Список производственных баз (ЦБЗ) с координатами.
-
Список автобетононасосов (АБН) с характеристиками, статусом и местоположением.
-
Глобальные настройки:
TIME_BUFFER_BETWEEN_SLOTS(в % или минутах),MINIMAL_TRUCK_LOAD_PERCENT.
Шаг 0.1: Валидация и нормализация данных
Для каждого заказа: 1. Проверить корректность данных 2. Рассчитать минимальное и максимальное время доставки 3. Привести желаемое окно клиента к стандартному формату 4. Вычислить коэффициент срочности = (дедлайн - текущее время) / общее время сменыШаг 0.2: Сортировка заказов по сложности выполнения
Сложность_заказа = (Приоритет_клиента × 0.4) + (Коэффициент_срочности × 0.3) + (Объём_заказа / Стандартный_объём × 0.2) + (Сложность_логистики × 0.1) Сортируем заказы по убыванию Сложности_заказаЭтап 1: Разбиение заказов на атомарные поставки
Шаг 1.1: Определение оптимального размера поставки
Для каждого заказа: Если Объём_заказа ≤ Максимальная_вместимость_машины: Количество_поставок = 1 Объём_поставки = Объём_заказа Иначе: Найти все доступные вместимости машин: C1, C2, ..., Ck Найти оптимальное разбиение, минимизирующее: Целевая_функция = α × Количество_поставок + β × (Сумма_остатков_в_машинах) + γ × (Максимальный_интервал_между_поставками)Пример расчёта для заказа 15 м³:
Доступные вместимости машин: 5 м³, 7 м³, 10 м³ Варианты разбиения: 1) 3 × 5 м³ = 15 м³ (остаток 0) ✓ 2) 2 × 7 м³ = 14 м³ (остаток 1 м³ - требует доп. машину 5 м³) 3) 1 × 10 м³ + 1 × 5 м³ = 15 м³ (остаток 0) ✓ Выбираем вариант 3, так как минимизирует количество поставок
Шаг 1.2: Создание сущностей поставок
Для каждой поставки: 1. Присвоить уникальный ID 2. Унаследовать данные от родительского заказа 3. Рассчитать параметры: - Минимальное время выполнения = Погрузка + Путь_туда + Разгрузка + Возврат - Время жизни бетона = 90 минут (для стандартного бетона) - Окончательный дедлайн = MIN(Дедлайн_клиента, Время_начала + Время_жизни)Этап 1а: Привязка заказов к ЦБЗ
Для каждого заказа рассчитывается расстояние/время до каждой доступной ЦБЗ (с учётом графика работы). Выбирается ЦБЗ с минимальным значением (время_доставки * Коэффициент_загрузки_базы). Заказ закрепляется за выбранной ЦБЗ. Все поставки по нему будут планироваться от этой базы.Этап 2: Группировка поставок для параллельной обработки
Шаг 2.1: Создание групп по ограничениям
Группа А: Поставки с жёсткими временными окнами (нельзя сдвигать) Группа Б: Поставки, требующие непрерывной заливки Группа В: Поставки для VIP-клиентов Группа Г: Стандартные поставки Группа Д: Поставки с гибкими временами Приоритет обработки: А → Б → В → Г → Д
Шаг 2.2: Внутригрупповая сортировка
Для каждой группы сортировка по: 1. Времени начала окна (от более раннего к более позднему) 2. Длительности окна (от более узкого к более широкому) 3. Объёму (от большего к меньшему)
Этап 3: Распределение поставок по машинам
Цикл обработки поставок:
Для каждой поставки в порядке приоритета групп: Шаг 3.1: Формирование пула кандидатов Для каждой машины проверяем: 1. Вместимость ≥ Объём_поставки 2. Техническая исправность = true 3. Машина доступна в течение смены 4. Машина может прибыть на завод к нужному времени 5. Доступное время работы водителя (Drivers.RemainingDutyTime) ≥ Продолжительность_слота 6. ТС должна быть в статусе "На линии" (Да) и приписана к ЦБЗ, за которой закреплён заказ (допускается привлечение машин с других баз в случае дефицита). 7. Для поставок, требующих АБН, формируется отдельный пул кандидатов среди доступных АБН. Шаг 3.2: Предварительная оценка кандидатов Для каждой машины-кандидата рассчитываем: Время_начала_минимальное = MAX(Текущее_свободное_время, Время_прибытия_на_завод) Время_окончания = Время_начала + Длительность_поставки Отсеиваем кандидатов, у которых: - Время_окончания > Окончательный_дедлайн - Время_окончания > Конец_смены - Время_разгрузки > Время_начала + Время_жизни_бетона Шаг 3.3: Детальный расчёт для каждого кандидата Для каждого оставшегося кандидата: 1. Рассчитать точное время всех этапов: - Выезд на завод: Время_начала - Путь_до_завода - Погрузка: 15-20 минут (зависит от объёма) - Путь к клиенту: Расстояние / Средняя_скорость × Коэффициент_пробок - Разгрузка: 2-3 минуты на м³ - Возврат: Расстояние_обратно / Средняя_скорость 2. Проверить пересечения с существующими слотами машины 3. Рассчитать буферы: - Операционный буфер: 10% от времени в пути - Рисковый буфер: 5-15 минут (зависит от сложности объекта) Шаг 3.4: Оценка и выбор лучшего кандидата Оценочная_функция(Машина, Поставка) = W1 × Оценка_времени + W2 × Оценка_расстояния + W3 × Оценка_использования + W4 × Оценка_качества Где: Оценка_времени = 1 / (Время_начала - Идеальное_время_начала)² Оценка_расстояния = 1 / (Порожний_пробег + 1) Оценка_использования = Объём_поставки / Вместимость_машины Оценка_качества = Коэффициент_приоритета_клиента W1, W2, W3, W4 — настраиваемые веса (по умолчанию: 0.4, 0.3, 0.2, 0.1) Шаг 3.5: Назначение и фиксация Если найден подходящий кандидат: - Закрепляем поставку за машиной - Создаём слот с рассчитанными временами - Обновляем доступное время машины - Добавляем в расписание Иначе: - Перемещаем поставку в очередь проблемных - Записываем причину неудачи Шаг 3.6: Резервирование буфера. После фиксации слота за ТС, следующий временной интервал длиной TIME_BUFFER_BETWEEN_SLOTS блокируется и не доступен для других назначений этой же машины.Этап 4: Обработка поставок, требующих непрерывной заливки
Особый алгоритм для заказов с непрерывной заливкой:
Для каждого заказа с требованием непрерывности: 1. Собрать все поставки этого заказа в группу 2. Определить требуемый интервал между поставками (например, ≤30 минут) 3. Найти машины, которые могут выполнить несколько поставок подряд: - Проверить возможность выполнения N поставок одной машиной - Рассчитать суммарное время и проверить попадание в окно клиента 4. Если одной машиной невозможно: - Найти несколько машин с максимально близкими временами разгрузки - Синхронизировать их расписание для минимизации интервалов 5. Провести корректировку: - Сдвинуть поставки для соблюдения интервала - Убедиться, что сдвиг не нарушает другие ограниченияЭтап 5: Пост-обработка и оптимизация
Шаг 5.1: Балансировка нагрузки
Для каждой машины рассчитываем: Коэффициент_загрузки = Суммарное_время_работы / Длительность_смены Средний_коэффициент = SUM(Коэффициент_загрузки) / Количество_машин Для машин с Коэффициент_загрузки > Средний_коэффициент + 0.2: Попробовать перенести часть поставок на менее загруженные машины
Шаг 5.2: Минимизация порожних пробегов
Для каждой последовательности поставок у машины: Рассчитать маршрут: База → Завод → Объект1 → Завод → Объект2 → ... Оценить порожний пробег между объектами Попробовать переставить поставки в последовательности для: - Уменьшения расстояния между объектами - Группировки поставок по географическим зонам
Шаг 5.3: Добавление защитных буферов
Для каждого слота в расписании: Если поставка критичная или объект сложный: Добавить_буфер = 15-20 минут Иначе если время в пути > 60 минут: Добавить_буфер = 10% от времени в пути Иначе: Добавить_буфер = 5 минут Распределить буфер: - 50% добавить перед разгрузкой (на случай задержек в пути) - 50% добавить после разгрузки (на случай задержек на объекте)Этап 6: Обработка проблемных поставок
Шаг 6.1: Анализ причин неудачи
Типичные причины: 1. Нехватка машин нужной вместимости 2. Отсутствие временных окон 3. Противоречивые ограничения 4. Невозможность соблюсти время жизни бетона
Шаг 6.2: Попытка перераспределения
Для каждой проблемной поставки: 1. Ослабить ограничения (если возможно): - Расширить временное окно - Разрешить использование машин большей вместимости - Увеличить максимальный интервал для непрерывной заливки 2. Попробовать занять резервное время других машин 3. Предложить разбить поставку на меньшие частиШаг 6.3: Эскалация к диспетчеру
Если автоматическое распределение невозможно: 1. Сформировать отчёт с причинами 2. Предложить варианты решения: - Добавить дополнительную машину - Перенести заказ на другую смену - Увеличить временное окно - Изменить параметры заказа 3. Передать задачу диспетчеру для ручного решенияЭтап 7: Синхронизация с автобетононасосами (АБН)
1. Для каждой поставки, требующей АБН, проверяется наличие забронированного слота у выбранного АБН. 2. Если слот не забронирован, осуществляется поиск свободного АБН, который сможет прибыть на объект к расчетному времени разгрузки АБС. 3. Время работы АБН привязывается ко времени начала разгрузки первой АБС на объекте.3. МАТЕМАТИЧЕСКАЯ ФОРМАЛИЗАЦИЯ
Основная целевая функция:
Минимизировать: Z = α×Z₁ + β×Z₂ + γ×Z₃ + δ×Z₄ Где: Z₁ = Σ(Время_доставки - Идеальное_время)² # Минимизация отклонений Z₂ = Σ(Порожний_пробег) # Минимизация пробегов Z₃ = Σ(1 - Коэффициент_заполнения)² # Максимизация использования Z₄ = Σ(Штрафы_за_нарушение_ограничений) # Минимизация нарушений
Ограничения:
1. ∀i: Время_начала_слота_i ≥ Время_окончания_слота_{i-1} + Время_перехода 2. ∀i: Время_разгрузки_i ≤ Время_погрузки_i + Время_жизни_бетона 3. ∀j: Σ(Объём_поставок_заказа_j) = Объём_заказа_j 4. ∀k: Σ(Время_работы_машины_k) ≤ Длительность_смены 5. ∀l,m: |Время_разгрузки_l - Время_разгрузки_m| ≤ Максимальный_интервал, если l и m принадлежат одному заказу с непрерывной заливкой4. ПРИМЕР РАСЧЁТА ДЛЯ КОНКРЕТНОГО СЦЕНАРИЯ
Исходные данные:
-
Смена: 07:00 - 19:00 (12 часов)
-
Парк: 5 машин (вместимости: 5, 5, 7, 7, 10 м³)
-
Завод: Координаты (55.7558, 37.6176)
-
Средняя скорость: 40 км/ч в городе, 60 км/ч за городом
Заказ 1:
-
Клиент: СтройГрад (приоритет: высокий)
-
Объём: 15 м³
-
Объект: 10 км от завода
-
Окно: 09:00 - 12:00
-
Требуется непрерывная заливка, макс. интервал 30 мин
Расчёт алгоритма:
Шаг 1: Разбиение заказа
Оптимальное разбиение: 10 м³ + 5 м³ Обоснование: Минимизация количества поставок (2 вместо 3)
Шаг 2: Расчёт временных параметров для поставки 10 м³
Время погрузки: 10 м³ × 3 мин/м³ = 30 минут Время в пути: 10 км / 40 км/ч = 15 минут Время разгрузки: 10 м³ × 2.5 мин/м³ = 25 минут Возврат: 10 км / 40 км/ч = 15 минут Итого: 30 + 15 + 25 + 15 = 85 минут Буфер: 10% = 9 минут Общее время слота: 94 минуты ≈ 1 час 34 минуты
Шаг 3: Поиск подходящей машины
Кандидаты по вместимости: машины 7 м³ и 10 м³ Машина 1 (7 м³): не подходит - объём 10 > 7 Машина 2 (7 м³): не подходит Машина 3 (10 м³): свободна с 07:00 Расчёт для машины 3: Выезд с базы: 07:00 Прибытие на завод: 07:15 Погрузка: 07:15 - 07:45 Путь к клиенту: 07:45 - 08:00 Разгрузка: 08:00 - 08:25 Возврат: 08:25 - 08:40 Проверка ограничений: ✓ Попадание в окно клиента (08:00 ∈ [09:00-12:00] - требуется корректировка) ✓ Время жизни бетона: 08:00 - 07:45 = 15 минут < 90 минут ✓ Конец слота 08:40 < конец смены 19:00
Шаг 4: Корректировка времени
Требуется сдвинуть на 1 час позже: Погрузка: 08:15 - 08:45 Разгрузка: 09:00 - 09:25 (попадает в окно) Обновлённый слот: 08:00 - 09:40
Шаг 5: Аналогичный расчёт для поставки 5 м³
Выбираем машину 5 м³, начинаем на 30 минут позже первой поставки для соблюдения непрерывной заливки: Разгрузка: 09:25 - 09:40 (интервал 0 минут ✓)
5. ОСОБЕННОСТИ РЕАЛИЗАЦИИ
5.1. Эвристические правила, используемые в алгоритме:
-
Правило ближайшего соседа:
-
После выполнения поставки на объекте, следующая поставка назначается на ближайший объект
-
-
Правило заполнения до конца:
-
Если осталось мало времени до конца смены, назначаются короткие поставки рядом с базой
-
-
Правило резервирования VIP:
-
Для VIP-клиентов резервируется 10% времени у лучших машин
-
-
Правило избегания пиков:
-
Стараться не назначать разгрузку в часы пик (08:00-10:00, 17:00-19:00)
-
5.2. Обработка конфликтов и тупиковых ситуаций:
Тупиковая ситуация: Нельзя назначить поставку без нарушения ограничений
Стратегии выхода:
-
Откат (Backtracking): Отменить последнее назначение и попробовать другой вариант
-
Ослабление ограничений: Временно разрешить небольшое нарушение
-
Разделение проблемы: Разделить сложную поставку на части
-
Перенос на потом: Отложить решение до обработки других поставок
5.3. Оптимизационные улучшения:
-
Локальный поиск: После построения расписания пытаться улучшить его небольшими изменениями
-
Табу-поиск: Запрещать возврат к недавно рассмотренным решениям
-
Имитация отжига: Иногда разрешать ухудшения для выхода из локальных оптимумов
6. ПРОИЗВОДИТЕЛЬНОСТЬ И МАСШТАБИРУЕМОСТЬ
Временная сложность:
O(N × M × K × L) Где: N - количество поставок M - количество машин K - среднее количество временных окон у машины L - сложность проверки ограничений Для типичного сценария (50 поставок, 10 машин): ≈ 50 × 10 × 5 × 10 = 25,000 операций Время выполнения: ~2-3 секунды
Память:
Требуется хранить: - Матрицу назначений: N × M элементов - Расписание каждой машины: M списков по ~10 элементов - Кэш рассчитанных расстояний: ~N² элементов Общий объём: O(N² + M × N) ≈ 100-500 КБ для типичного сценария
7. ВАЛИДАЦИЯ И ТЕСТИРОВАНИЕ АЛГОРИТМА
Тестовые сценарии:
-
Идеальный случай: Все поставки могут быть назначены без конфликтов
-
Предельная загрузка: Количество поставок на пределе возможностей парка
-
Конфликт ограничений: Противоречивые требования клиентов
-
Каскадный сбой: Отказ ключевой машины в начале смены
Метрики качества расписания:
1. Коэффициент использования машин: Должен быть 70-90% 2. Среднее отклонение от идеального времени: Должно быть < 30 минут 3. Количество нарушений ограничений: Должно быть 0 4. Суммарный порожний пробег: Минимизируется 5. Баланс загрузки: Разница загрузки машин < 20%
8. ИНТЕГРАЦИЯ С ДРУГИМИ СИСТЕМАМИ
Алгоритм получает данные из:
-
CRM-системы — информация о клиентах и их приоритетах
-
ERP-системы — данные о заказах и производственных мощностях
-
GPS-трекера — текущее положение машин
-
Картографических сервисов — актуальные данные о пробках и маршрутах
-
Погодных сервисов — прогноз для корректировки времени в пути
9. НАСТРОЙКА И КАЛИБРОВКА
Алгоритм имеет настраиваемые параметры:
# Веса в оценочной функции WEIGHTS = { 'time_deviation': 0.4, # Важность соблюдения времени 'distance': 0.3, # Важность минимизации пробега 'capacity_utilization': 0.2, # Важность заполнения машины 'client_priority': 0.1 # Важность приоритета клиента } # Буферы и допуски TOLERANCES = { 'time_window': 15, # Допустимое отклонение от окна (мин) 'continuous_pouring': 5, # Допуск по интервалу непрерывности (мин) 'concrete_lifetime': 10 # Запас по времени жизни бетона (мин) } # Стратегические параметры STRATEGY = { 'reserve_vip_capacity': 0.1, # Резерв для VIP-клиентов (10%) 'max_backtracking_depth': 3, # Макс. глубина отката 'optimization_iterations': 100 # Количество итераций оптимизации }10. ПРАКТИЧЕСКИЕ РЕКОМЕНДАЦИИ ПО РЕАЛИЗАЦИИ
-
Начинать с простого: Сначала реализовать базовый жадный алгоритм без оптимизации
-
Добавлять сложность постепенно: Поэтапно вводить дополнительные ограничения и оптимизации
-
Использовать кэширование: Кэшировать результаты расчёта расстояний и проверок
-
Реализовать инкрементальное обновление: При изменении одной поставки не пересчитывать всё расписание
-
Предусмотреть ручное вмешательство: Возможность диспетчера корректировать автоматические решения
ЗАКЛЮЧЕНИЕ
Алгоритм первоначального распределения представляет собой сбалансированную комбинацию эвристических правил и оптимизационных техник, которая позволяет быстро строить качественное расписание даже для сложных сценариев. Его ключевые преимущества:
-
Гарантированное нахождение решения (если оно существует)
-
Учёт всех технологических ограничений цементной логистики
-
Баланс между оптимальностью и скоростью работы
-
Возможность каскадной обработки — сначала сложные, потом простые задачи
-
Интеграция с системами реального времени для учёта текущей обстановки
Алгоритм является основой всей системы планирования и обеспечивает стабильную работу даже в условиях высокой нагрузки и неопределённости.
Приложение №2
ДЕТАЛЬНОЕ ОПИСАНИЕ АЛГОРИТМА КАСКАДНОГО ПЕРЕРАСЧЕТА
1. ФИЛОСОФИЯ АЛГОРИТМА: УПРАВЛЕНИЕ ХАОСОМ В РЕАЛЬНОМ ВРЕМЕНИ
Алгоритм каскадного перерасчёта — это интеллектуальная система экстренного реагирования, которая превращает хаотичные сбои в управляемые изменения расписания. Он работает по принципу "минимального необходимого вмешательства" — как хирург, который делает точечные разрезы, а не ампутирует конечности. Алгоритм реализует полуавтоматический подход. Система выполняет анализ, изоляцию проблемы и генерацию вариантов решений, но финальное утверждение любого изменения расписания всегда остаётся за диспетчером. Это особенно важно при обработке таких событий, как отклонение заказа водителем или ручное снятие ТС с линии.
Ментальная модель: Представьте домино. Одно падающее костяшка (сбой) может уронить всю цепь (расписание). Наш алгоритм — это рука, которая подхватывает упавшие костяшки и расставляет их на новые места, не давая упасть остальным.
2. КЛАССИФИКАЦИЯ СОБЫТИЙ И СТРАТЕГИИ РЕАКЦИИ
2.1. Матрица событий и их каскадных эффектов:
Событие Непосредственный эффект Каскадный эффект Время реакции Приоритет обработки Полный отказ машины Машина выбывает до конца смены Все будущие слоты освобождаются 0-2 минуты Критический (1) Частичная поломка Машина встанет на 2-4 часа Слоты в периоде простоя сдвигаются 2-5 минут Высокий (2) ДТП без пострадавших Машина задержана на 1-3 часа Текущая поставка отменяется, следующие сдвигаются 5-10 минут Высокий (2) Задержка на разгрузке Текущий слот удлиняется на X минут Последующие слоты этой машины сдвигаются 1-3 минуты Средний (3) Пробки на маршруте Увеличение времени в пути на Y% Риск превышения времени жизни бетона 2-5 минут Средний (3) Отмена заказа клиентом Освобождается N слотов Появляется резерв для других поставок 1-2 минуты Низкий (4) Новая доступная машина Увеличивается мощность парка Возможность оптимизации нагрузки 3-7 минут Низкий (4) Отклонение заказа водителем Освобождается конкретный слот у конкретного ТС. Сдвиг последующих слотов этого ТС. Риск срыва времени доставки. 1-3 мин Высокий (2) Изменение статуса ТС "На линии" на "Нет" ТС исключается из пула доступных. Все будущие слоты этой ТС освобождаются. Требуется перераспределение. 2-5 мин Критический (1) 2.2. Жизненный цикл обработки события:
1. ДЕТЕКЦИЯ (0-30 секунд) │ 2. ВАЛИДАЦИЯ (30-60 секунд) │ 3. ОЦЕНКА ВОЗДЕЙСТВИЯ (60-90 секунд) │ 4. РАЗРАБОТКА СТРАТЕГИИ (90-120 секунд) │ 5. ВЫПОЛНЕНИЕ ПЕРЕРАСЧЕТА (120-300 секунд) │ 6. ВАЛИДАЦИЯ РЕЗУЛЬТАТА (300-360 секунд) │ 7. УВЕДОМЛЕНИЕ СТОРОН (360-420 секунд)
3. ДЕТАЛЬНЫЙ АЛГОРИТМ ДЛЯ КРИТИЧЕСКОГО СОБЫТИЯ: ПОЛНАЯ ПОЛОМКА МАШИНЫ
ФАЗА 1: ЭКСПРЕСС-ДИАГНОСТИКА (0-60 секунд)
def emergency_assessment(event): """ Молниеносная оценка ситуации """ # Шаг 1.1: Определение точки невозврата breakdown_time = event.occurred_at truck = event.related_truck # Какие поставки УЖЕ НЕВОЗМОЖНО выполнить immediate_impact = [] for slot in truck.schedule: if slot.start_time <= breakdown_time <= slot.end_time: # Текущая поставка - экстренная ситуация current_delivery = slot.delivery if current_delivery.is_in_transit(): # Бетон уже в пути - критично! cement_age = breakdown_time - current_delivery.mixing_start_time remaining_lifetime = current_delivery.concrete_lifetime - cement_age if remaining_lifetime < TimeSpan.FromMinutes(30): # Бетон скоро схватится - нужна срочная замена immediate_impact.append({ 'delivery': current_delivery, 'type': 'CRITICAL_CEMENT_AT_RISK', 'remaining_minutes': remaining_lifetime.total_minutes, 'required_action': 'IMMEDIATE_REASSIGNMENT' }) # Шаг 1.2: Быстрая инвентаризация ресурсов available_trucks = get_available_trucks( from_time=breakdown_time, min_capacity=5, # минимальная вместимость proximity_to_plant=True ) # Шаг 1.3: Расчет окна возможностей opportunity_window = calculate_opportunity_window( broken_truck=truck, available_trucks=available_trucks, time_now=breakdown_time ) return { 'immediate_crises': immediate_impact, 'available_resources': available_trucks, 'window_of_opportunity': opportunity_window, 'severity_level': calculate_severity(immediate_impact) }ФАЗА 2: СТРАТЕГИЧЕСКОЕ ПЛАНИРОВАНИЕ (60-120 секунд)
def develop_rescue_strategy(assessment): """ Разработка многоуровневой стратегии спасения """ strategy = { 'phase_1': [], # Действия в ближайшие 15 минут 'phase_2': [], # Действия в ближайший час 'phase_3': [], # Действия на оставшуюся смену 'fallback_plans': [] # Резервные варианты } # УРОВЕНЬ 1: Спасение бетона, который уже в пути for crisis in assessment['immediate_crises']: if crisis['type'] == 'CRITICAL_CEMENT_AT_RISK': rescue_plan = create_cement_rescue_plan( delivery=crisis['delivery'], time_limit=crisis['remaining_minutes'], available_trucks=assessment['available_resources'] ) if rescue_plan['feasible']: strategy['phase_1'].append({ 'action': 'EMERGENCY_TRANSFER', 'plan': rescue_plan, 'priority': 'CRITICAL' }) else: # Невозможно спасти - план минимизации убытков strategy['phase_1'].append({ 'action': 'DAMAGE_CONTROL', 'plan': create_damage_control_plan(crisis['delivery']), 'priority': 'CRITICAL' }) # УРОВЕНЬ 2: Перераспределение ближайших поставок (15-60 минут) immediate_slots = get_immediate_slots( truck=assessment['broken_truck'], time_horizon=TimeSpan.FromHours(2), from_time=assessment['breakdown_time'] ) for slot in immediate_slots: reassignment_plan = create_slot_reassignment_plan( slot=slot, available_trucks=assessment['available_resources'], strategy='NEAREST_FIT' ) strategy['phase_2'].append({ 'action': 'SLOT_REASSIGNMENT', 'slot': slot, 'plan': reassignment_plan, 'priority': 'HIGH' if slot.delivery.client.priority >= 8 else 'MEDIUM' }) # УРОВЕНЬ 3: Оптимизация оставшейся смены remaining_slots = get_remaining_slots( truck=assessment['broken_truck'], from_time=assessment['breakdown_time'] + TimeSpan.FromHours(2) ) optimization_strategy = create_optimization_strategy( slots=remaining_slots, available_trucks=assessment['available_resources'], time_constraints=assessment['window_of_opportunity'] ) strategy['phase_3'] = optimization_strategy # Резервные планы strategy['fallback_plans'] = create_fallback_plans(strategy) return strategyФАЗА 3: КАСКАДНЫЙ ПЕРЕРАСЧЕТ С УПРАВЛЯЕМЫМ РАСПРОСТРАНЕНИЕМ
def execute_cascade_reschedule(strategy, original_schedule): """ Выполнение каскадного перерасчета с контролем распространения """ # Шаг 3.1: Создание "песочницы" для экспериментов sandbox_schedule = original_schedule.clone() change_log = [] # Шаг 3.2: Последовательное выполнение фаз стратегии for phase_name in ['phase_1', 'phase_2', 'phase_3']: phase_actions = strategy[phase_name] for action in phase_actions: result = execute_action_in_sandbox( action=action, schedule=sandbox_schedule, change_log=change_log ) if not result['success']: # Действие не удалось - активируем механизм компенсации compensation = create_compensation_plan( failed_action=action, failure_reason=result['reason'], current_state=sandbox_schedule ) # Пытаемся выполнить компенсацию compensation_result = execute_compensation( compensation_plan=compensation, schedule=sandbox_schedule ) if not compensation_result['success']: # Каскадная неудача - эскалация escalate_to_human( action=action, compensation=compensation, current_state=sandbox_schedule ) # Шаг 3.3: Проверка целостности нового расписания integrity_check = validate_schedule_integrity(sandbox_schedule) if integrity_check['valid']: # Шаг 3.4: Постепенное применение изменений final_schedule = apply_changes_gradually( original=original_schedule, new=sandbox_schedule, change_log=change_log ) return { 'success': True, 'schedule': final_schedule, 'changes_made': len(change_log), 'cascade_depth': calculate_cascade_depth(change_log), 'estimated_impact': calculate_impact_metrics(change_log) } else: # Не удалось построить валидное расписание return { 'success': False, 'reason': integrity_check['violations'], 'fallback_activated': True }4. АЛГОРИТМ ПЕРЕРАСЧЕТА ПРИ ЗАДЕРЖКЕ НА РАЗГРУЗКЕ
Специфика: Задержка вызывает цепную реакцию, но не требует смены машины.
def handle_unloading_delay(event): """ Обработка задержки на разгрузке с минимизацией каскадного эффекта """ # Шаг 1: Точное измерение задержки delay = event.delay_minutes affected_slot = event.related_slot truck = affected_slot.truck # Шаг 2: Анализ "эластичности" временных окон elasticity_analysis = analyze_time_elasticity( slot=affected_slot, requested_delay=delay ) # Шаг 3: Многоуровневая стратегия поглощения задержки # Уровень 1: Поглощение за счет внутренних резервов if elasticity_analysis['can_absorb_without_shift']: # Задержку можно поглотить за счет буферов adjusted_schedule = absorb_delay_internally( schedule=current_schedule, slot=affected_slot, delay=delay ) # Уровень 2: Минимальный сдвиг с компенсацией elif elasticity_analysis['can_shift_with_minimal_impact']: # Находим оптимальную точку сдвига shift_point = find_optimal_shift_point( truck_schedule=truck.schedule, delayed_slot=affected_slot, delay=delay ) # Выполняем "умный" сдвиг adjusted_schedule = execute_smart_shift( schedule=current_schedule, shift_from=shift_point, shift_amount=delay, strategy='MINIMAL_DISTURBANCE' ) # Уровень 3: Каскадный перерасчет с изоляцией else: # Изолируем область воздействия impact_zone = isolate_impact_zone( schedule=current_schedule, epicenter=affected_slot, max_ripple_hours=2 # Ограничиваем распространение 2 часами ) # Перераспределяем в изолированной зоне adjusted_schedule = reschedule_within_zone( schedule=current_schedule, impact_zone=impact_zone, delay_source=affected_slot ) # Шаг 4: Проверка и компенсация compensation_needed = check_for_compensation_needs(adjusted_schedule) if compensation_needed: adjusted_schedule = apply_compensation_measures( schedule=adjusted_schedule, compensation_plan=compensation_needed ) return adjusted_schedule5. ИНТЕЛЛЕКТУАЛЬНЫЙ МЕХАНИЗМ ПРЕДОТВРАЩЕНИЯ КАСКАДНЫХ СБОЕВ
5.1. Алгоритм "Умной изоляции":
def intelligent_impact_isolation(schedule, failure_point): """ Изоляция области воздействия сбытия с минимизацией распространения """ # Шаг 1: Определение "эпицентра" и "эпицентральной зоны" epicenter = failure_point epicentral_zone = calculate_epicentral_zone( epicenter=epicenter, radius_hours=1, # Первый час - максимальное воздействие schedule=schedule ) # Шаг 2: Идентификация "амортизаторов" - поставок, которые могут сдвинуться без последствий shock_absorbers = identify_shock_absorbers( schedule=schedule, around_zone=epicentral_zone, buffer_size=2 # 2 слота в каждую сторону ) # Шаг 3: Создание "защитного периметра" protective_perimeter = create_protective_perimeter( schedule=schedule, inner_zone=epicentral_zone, outer_radius_hours=3 ) # Шаг 4: Расчет "коэффициента упругости" для каждого слота elasticity_map = calculate_slot_elasticity( schedule=schedule, zone=epicentral_zone + protective_perimeter ) return { 'epicenter': epicenter, 'epicentral_zone': epicentral_zone, 'shock_absorbers': shock_absorbers, 'protective_perimeter': protective_perimeter, 'elasticity_map': elasticity_map, 'isolation_strategy': 'ADAPTIVE_CONTAINMENT' }5.2. Алгоритм "Приоритетного спасения":
def priority_based_rescue(schedule, affected_slots): """ Спасение поставок по приоритету с учетом многомерных критериев """ # Многомерная оценка критичности каждой поставки criticality_scores = [] for slot in affected_slots: score = calculate_multidimensional_criticality( slot=slot, dimensions=[ 'CLIENT_PRIORITY', # Важность клиента 'CEMENT_VIABILITY', # Риск схватывания бетона 'CONTRACT_PENALTY', # Штрафы за срыв 'LOGISTIC_COMPLEXITY', # Сложность замены 'IMPACT_ON_OTHERS' # Влияние на другие поставки ] ) criticality_scores.append({ 'slot': slot, 'score': score, 'rescue_window': calculate_rescue_window(slot), 'rescue_options': find_rescue_options(slot, schedule) }) # Сортировка по критичности и доступности вариантов спасения criticality_scores.sort( key=lambda x: ( -x['score']['overall'], # По убыванию критичности len(x['rescue_options']), # По количеству вариантов x['rescue_window']['minutes_remaining'] # По оставшемуся времени ) ) # Последовательное спасение rescued_slots = [] failed_rescues = [] for item in criticality_scores: rescue_result = attempt_slot_rescue( slot=item['slot'], options=item['rescue_options'], schedule=schedule, time_limit=item['rescue_window']['minutes_remaining'] ) if rescue_result['success']: rescued_slots.append({ 'slot': item['slot'], 'new_assignment': rescue_result['new_assignment'] }) schedule = rescue_result['updated_schedule'] else: failed_rescues.append({ 'slot': item['slot'], 'reason': rescue_result['failure_reason'], 'suggested_actions': rescue_result['suggestions'] }) return { 'rescued_count': len(rescued_slots), 'failed_count': len(failed_rescues), 'rescued_slots': rescued_slots, 'failed_rescues': failed_rescues, 'final_schedule': schedule, 'rescue_efficiency': len(rescued_slots) / len(affected_slots) }6. АЛГОРИТМ ОБРАБОТКИ МНОЖЕСТВЕННЫХ СБОЕВ
Сценарий: Одновременная поломка 2 машин + задержка на 3 объектах
def handle_multiple_failures(failure_events): """ Обработка множественных одновременных сбоев """ # Шаг 1: Кластеризация сбоев по времени и местоположению failure_clusters = cluster_failures( events=failure_events, time_threshold=TimeSpan.FromMinutes(30), location_threshold=5 # км ) # Шаг 2: Определение доминирующего сбоя в каждом кластере dominant_failures = [] for cluster in failure_clusters: dominant = find_dominant_failure(cluster) dominant_failures.append(dominant) # Шаг 3: Последовательная обработка доминирующих сбоев # с учетом их взаимного влияния current_schedule = get_current_schedule() for i, failure in enumerate(dominant_failures): # Учитываем изменения, внесенные обработкой предыдущих сбоев impact_forecast = forecast_cross_impact( failure=failure, already_handled=dominant_failures[:i], current_schedule=current_schedule ) # Адаптивная стратегия с учетом прогноза strategy = adapt_strategy_based_on_forecast( base_strategy=get_base_strategy(failure), impact_forecast=impact_forecast, remaining_failures=dominant_failures[i+1:] ) # Выполнение с компенсацией побочных эффектов result = execute_with_side_effect_compensation( strategy=strategy, schedule=current_schedule, compensation_buffer=TimeSpan.FromMinutes(15) ) current_schedule = result['schedule'] # Если достигнут предел устойчивости - остановка if result['system_stability'] < 0.6: # Порог устойчивости emergency_stabilization(current_schedule) break # Шаг 4: Глобальная оптимизация после экстренных мер optimized_schedule = global_post_crisis_optimization( schedule=current_schedule, optimization_criteria=['STABILITY', 'FAIRNESS', 'EFFICIENCY'] ) return optimized_schedule7. МЕХАНИЗМЫ КОМПЕНСАЦИИ И ВОССТАНОВЛЕНИЯ
7.1. Алгоритм распределения компенсационных буферов:
def redistribute_compensation_buffers(schedule, stress_points): """ Перераспределение временных буферов для компенсации сбоев """ # Шаг 1: Идентификация "доноров" буферов buffer_donors = find_buffer_donors( schedule=schedule, criteria=[ 'HAS_EXCESS_BUFFER', # Имеет избыточный буфер 'LOW_RISK_PROFILE', # Низкий риск сбоев 'FLEXIBLE_TIME_WINDOW', # Гибкое временное окно 'NON_CRITICAL_CLIENT' # Не критичный клиент ] ) # Шаг 2: Идентификация "реципиентов" буферов buffer_recipients = find_buffer_recipients( schedule=schedule, stress_points=stress_points, criteria=[ 'HIGH_RISK_PROFILE', # Высокий риск 'TIGHT_TIME_WINDOW', # Жесткое окно 'CRITICAL_CLIENT', # Важный клиент 'MINIMAL_BUFFER' # Мало буфера ] ) # Шаг 3: Оптимальное перераспределение redistribution_plan = optimize_buffer_redistribution( donors=buffer_donors, recipients=buffer_recipients, schedule=schedule, objective='MAXIMIZE_SYSTEM_STABILITY' ) # Шаг 4: Поэтапное применение new_schedule = apply_buffer_redistribution( schedule=schedule, plan=redistribution_plan, phase_duration=TimeSpan.FromMinutes(5) # Постепенно, по 5 минут ) return new_schedule7.2. Алгоритм восстановления после каскадного сбоя:
def post_cascade_recovery(schedule, cascade_event): """ Восстановление системы после серьезного каскадного сбоя """ recovery_phases = [ { 'name': 'СТАБИЛИЗАЦИЯ', 'duration': TimeSpan.FromMinutes(30), 'objectives': ['STOP_CASCADE', 'PROTECT_CRITICAL', 'ISOLATE_DAMAGE'] }, { 'name': 'ВОССТАНОВЛЕНИЕ', 'duration': TimeSpan.FromHours(2), 'objectives': ['RESTORE_CAPACITY', 'REASSIGN_URGENT', 'OPTIMIZE_LOCALLY'] }, { 'name': 'ОПТИМИЗАЦИЯ', 'duration': TimeSpan.FromHours(4), 'objectives': ['GLOBAL_OPTIMIZATION', 'LOAD_BALANCING', 'BUFFER_RESTORATION'] } ] recovered_schedule = schedule for phase in recovery_phases: phase_strategy = create_recovery_strategy( phase=phase, current_state=recovered_schedule, cascade_history=cascade_event.history ) phase_result = execute_recovery_phase( strategy=phase_strategy, schedule=recovered_schedule, time_limit=phase['duration'] ) recovered_schedule = phase_result['schedule'] # Проверка готовности к следующей фазе if not phase_result['phase_successful']: # Расширяем текущую фазу phase['duration'] += TimeSpan.FromMinutes(15) continue # Мониторинг прогресса восстановления recovery_metrics = calculate_recovery_metrics( original=schedule, current=recovered_schedule, phase=phase['name'] ) if recovery_metrics['stability_index'] >= 0.8: # Достигнута достаточная стабильность - переход к следующей фазе continue else: # Требуется дополнительное время phase['duration'] += TimeSpan.FromMinutes(30) # Финальная проверка final_validation = validate_recovery_completion( original_schedule=schedule, recovered_schedule=recovered_schedule, cascade_event=cascade_event ) if final_validation['recovery_successful']: return { 'status': 'FULL_RECOVERY', 'schedule': recovered_schedule, 'recovery_time': final_validation['total_recovery_time'], 'efficiency_loss': final_validation['efficiency_loss_percentage'] } else: return { 'status': 'PARTIAL_RECOVERY', 'schedule': recovered_schedule, 'unresolved_issues': final_validation['remaining_issues'], 'human_intervention_required': True }8. ИНТЕЛЛЕКТУАЛЬНАЯ СИСТЕМА ПРИНЯТИЯ РЕШЕНИЙ
8.1. Нейросетевая оценка вариантов перерасчета:
Архитектура нейросети для оценки вариантов: Входной слой (12 параметров): 1. Количество затронутых поставок 2. Средний приоритет клиентов 3. Общий объем риска (м³×приоритет) 4. Временной горизонт воздействия 5. Количество доступных машин 6. Среднее расстояние до объектов 7. Коэффициент заполнения машин 8. Запас по времени жизни бетона 9. Сложность логистики (1-10) 10. Погодные условия (индекс) 11. Дорожная ситуация (индекс) 12. Историческая надежность варианта Скрытые слои (3 слоя по 8 нейронов): - Анализ взаимосвязей параметров - Выявление неочевидных паттернов - Оценка рисков и возможностей Выходной слой (4 оценки): 1. Вероятность успеха (0-1) 2. Ожидаемое время восстановления (минуты) 3. Прогнозируемые потери (денежные) 4. Качество расписания после (0-100)
8.2. Алгоритм принятия решений на основе ML:
def ml_enhanced_decision_making(options, historical_data): """ Принятие решений с использованием машинного обучения """ # Шаг 1: Извлечение признаков для каждого варианта feature_vectors = [] for option in options: features = extract_features(option) feature_vectors.append(features) # Шаг 2: Прогнозирование результатов с помощью обученной модели predictions = prediction_model.predict(feature_vectors) # Шаг 3: Многокритериальная оптимизация optimal_option = multi_criteria_optimization( options=options, predictions=predictions, criteria_weights={ 'success_probability': 0.35, 'recovery_time': 0.25, 'financial_impact': 0.20, 'schedule_quality': 0.20 } ) # Шаг 4: Проверка на аномалии anomaly_check = detect_anomalies( selected_option=optimal_option, historical_patterns=historical_data ) if anomaly_check['is_anomaly']: # Выбор второго лучшего варианта optimal_option = get_second_best( options=options, predictions=predictions ) return optimal_option9. СИСТЕМА МОНИТОРИНГА И ПРОГНОЗИРОВАНИЯ КАСКАДОВ
9.1. Алгоритм раннего предупреждения:
def early_cascade_warning_system(schedule): """ Система раннего предупреждения о потенциальных каскадных сбоях """ # Шаг 1: Поиск "точек напряжения" в расписании stress_points = find_schedule_stress_points( schedule=schedule, indicators=[ 'BACK_TO_BACK_SLOTS', # Слоты без буфера 'TIGHT_TIME_WINDOWS', # Жесткие окна клиентов 'HIGH_RISK_COMBINATIONS', # Рискованные комбинации поставок 'OVERLOADED_TRUCKS', # Перегруженные машины 'GEOGRAPHIC_CONFLICTS' # Географические конфликты ] ) # Шаг 2: Расчет "индекса каскадного риска" для каждой точки cascade_risk_index = {} for point in stress_points: risk_score = calculate_cascade_risk( stress_point=point, schedule=schedule, historical_failures=load_failure_history() ) cascade_risk_index[point] = risk_score # Шаг 3: Прогнозирование потенциальных каскадов potential_cascades = forecast_potential_cascades( stress_points=stress_points, risk_index=cascade_risk_index, simulation_count=1000 # Монте-Карло симуляция ) # Шаг 4: Генерация превентивных рекомендаций preventive_recommendations = generate_preventive_recommendations( potential_cascades=potential_cascades, schedule=schedule, intervention_cost_threshold=10000 # Максимальная стоимость вмешательства ) return { 'high_risk_points': cascade_risk_index, 'potential_cascades': potential_cascades, 'preventive_actions': preventive_recommendations, 'overall_risk_level': calculate_overall_risk_level(cascade_risk_index) }10. ПРАКТИЧЕСКАЯ РЕАЛИЗАЦИЯ: ОГРАНИЧЕНИЯ И ОПТИМИЗАЦИИ
10.1. Ограничения реального времени:
def real_time_constrained_rescheduling(event, time_budget): """ Перерасчет с жестким ограничением по времени """ # Шаг 1: Быстрая оценка сложности complexity = estimate_rescheduling_complexity(event) # Шаг 2: Выбор стратегии в зависимости от доступного времени if time_budget < TimeSpan.FromMinutes(2): strategy = 'ULTRA_FAST_HEURISTIC' max_iterations = 100 search_depth = 1 elif time_budget < TimeSpan.FromMinutes(5): strategy = 'FAST_LOCAL_SEARCH' max_iterations = 1000 search_depth = 2 elif time_budget < TimeSpan.FromMinutes(10): strategy = 'BALANCED_OPTIMIZATION' max_iterations = 5000 search_depth = 3 else: strategy = 'COMPREHENSIVE_SEARCH' max_iterations = 20000 search_depth = 4 # Шаг 3: Адаптивный алгоритм с контролем времени start_time = datetime.now() best_solution = None while (datetime.now() - start_time) < time_budget: candidate = generate_candidate_solution( event=event, strategy=strategy, current_best=best_solution ) candidate_score = evaluate_solution(candidate) if best_solution is None or candidate_score > best_solution['score']: best_solution = { 'schedule': candidate, 'score': candidate_score, 'time_spent': datetime.now() - start_time } # Проверка прогресса if should_terminate_early( current_best=best_solution, time_remaining=time_budget - (datetime.now() - start_time), progress_rate=calculate_progress_rate() ): break return best_solution['schedule']10.2. Балансировка качества и скорости:
Режим работы Время на перерасчет Качество решения Используется когда Экстренный 30-60 секунд 60-70% от оптимального Поломка в час пик, риск схватывания бетона Оперативный 2-5 минут 75-85% от оптимального Стандартные сбои в рабочее время Тщательный 5-10 минут 85-95% от оптимального Плановые изменения, оптимизация Аналитический 10-20 минут 95-99% от оптимального Анализ после смены, обучение системы 11. АЛГОРИТМ ОБРАБОТКИ ОТКЛОНЕНИЯ ЗАКАЗА ВОДИТЕЛЕМ
-
Детекция: Система получает событие от мобильного приложения:
{водитель_id, заказ_id, причина, timestamp}. -
Изоляция: Заказ переводится в статус
Отклонён. Его слот у конкретного ТС освобождается. -
Анализ воздействия: Определяются все последующие слоты этого же ТС. Они переводятся в статус
На перепланировании. -
Генерация вариантов (без автоматического применения):
-
Вариант А (приоритетный): Попытка найти другого водителя (ТС) для выполнения отклонённого заказа в тот же временной слот.
-
Вариант Б: Сдвиг отклонённого заказа на ближайший свободный слот с перераспределением последующих слотов исходного ТС.
-
-
Уведомление диспетчера: Система подсвечивает на диаграмме Ганта отклонённый заказ и затронутые слоты. Диспетчеру предлагаются сгенерированные варианты.
-
Утверждение: Диспетчер выбирает вариант, вносит при необходимости ручные корректировки и явно подтверждает новое расписание.
12. АЛГОРИТМ ОБРАБОТКИ ИЗМЕНЕНИЯ СТАТУСА ТС "НА ЛИНИИ"
-
Инициация: Диспетчер вручную изменяет значение поля
На линиинаНетдля конкретного ТС в справочнике. -
Валидация: Система проверяет, есть ли у данного ТС назначенные, но ещё не начатые заказы (слоты) на будущее время.
-
Изоляция и эскалация: Если такие заказы есть:
-
Все эти заказы переводятся в статус
На перепланировании. -
Диспетчеру немедленно выдается критическое уведомление со списком затронутых заказов.
-
Система не выполняет автоматический перерасчет. Диспетчер должен вручную инициировать процесс перепланирования для каждого заказа или использовать функцию массового поиска альтернатив.
-
ЗАКЛЮЧЕНИЕ: ФИЛОСОФИЯ УПРАВЛЕНИЯ ХАОСОМ
Алгоритм каскадного перерасчета — это живая, адаптивная система, которая эволюционирует с каждым обработанным сбоем. Её ключевые принципы:
-
Принцип минимального вмешательства: Менять только то, что необходимо
-
Принцип управляемого распространения: Контролировать границы воздействия
-
Принцип приоритетного спасения: Сначала важное, потом остальное
-
Принцип обучаемости: Каждый сбой делает систему умнее
-
Принцип отказоустойчивости: Всегда иметь план Б, В и Г
Итоговая формула успеха:
Эффективность_перерасчета = (Скорость_реакции × 0.3) + (Качество_решения × 0.4) + (Минимизация_изменений × 0.2) + (Удовлетворенность_клиентов × 0.1)
Этот алгоритм превращает хаотичные сбои из угрозы в возможность — возможность оптимизировать, учиться и становиться устойчивее с каждым днем.
-