Привет, Хабр! Сегодня мы погрузимся в увлекательный мир роевого интеллекта и децентрализованных систем. Я покажу, как простые правила, заложенные в каждый элемент системы, позволяют добиться сложного группового поведения без единого центра управления. В качестве полигона используем виртуальный рой автономных дронов.
*Код и симуляция: Python 3.8+, matplotlib, numpy
Проблема централизованного управления
Представьте, что вам нужно координировать движение 50 дронов. Первое, что приходит в голову — центральный контроллер с нейронной сетью, которая вычисляет оптимальные траектории для каждого аппарата. Но у этого подхода есть фундаментальные недостатки:
Единая точка отказа — выход контроллера из строя парализует всю систему
Вычислительная сложность — задача O(n²) и выше для n агентов
Низкая отказоустойчивость — потеря связи с одним дроном может нарушить весь план
Плохая масштабируемость
Альтернатива? Децентрализованное управление, где каждый дрон принимает решения самостоятельно, основываясь лишь на информации от ближайших соседей.
Три кита роевого интеллекта
В основе нашего подхода лежат три простых правила, вдохновленных поведением стай птиц и косяков рыб:
1. Избегание столкновений
Самый приоритетный rule: не врезаться в соседей.
# Упрощенная логика отталкивания
if dist < self.desired_distance:
repulsion = True
k = (self.desired_distance / dist)*3
dx = drone.x - n.x
dy = drone.y - n.y
repulsion_x += (dx / dist) * k
repulsion_y += (dy / dist) * k
Обратите внимание на кубическую зависимость (**3) — чем ближе сосед, тем сильнее отталкивание. Это создает "буфер безопасности" вокруг каждого дрона.
2. Сплочение группы
Если соседи слишком далеко — приближаемся к ним, поддерживая целостность группы:
# Упрощенная логика сплолчения группы
if dist > self.desired_distance * 1.2:
k = k * self.desired_distance / (dist - self.desired_distance)
dx = n.x - drone.x
dy = n.y - drone.y
attraction_x += k * dx / dist
attraction_y += k * dy / dist
Ближайшие соседи более приоритетны, что обеспечивается знаменателем коэффициента.
3. Движение к цели
Каждый дрон знает общую цель (в нашем случае — координаты [0,0]) и постепенно смещается к ней:
dist = np.sqrt((drone.x- target.x) ** 2 + (drone.y - target.y) ** 2)
if dist > 0:
striving_x = - drone.x * k
striving_y = - drone.y * k
Архитектура системы
Давайте разберем основные компоненты нашей симуляции:
Класс Drone — кирпичик роя
class Drone:
def __init__(self, id, x=0, y=0):
self.id = id
self.x = x
self.y = y
self.vx = 0
self.vy = 0
self.radius = 0.3
self.active = True
Каждый дрон знает только свою позицию и статус. Никакой информации о глобальной структуре!
Swarm — emergent intelligence
Класс Swarm не управляет дронами напрямую. Вместо этого он обеспечивает среду для их взаимодействия.
Дальность локально взаимодействия дронов ограничена параметром self.neighbor_radius:
def find_neighbors(self, drone):
"""Возвращает список ближайших активных дронов"""
neighbors = []
for d in self.drones:
if d.active and d != drone:
if drone.distance_to(d) < self.neighbor_radius:
neighbors.append(d)
return neighbors
В пределах этого радиуса соседние дроны считаются частью группы.
Эмерджентное поведение в действии
Что удивительно — из простых локальных правил рождается сложное глобальное поведение:
Самоорганизация — изначально случайное расположение быстро структурируется
Адаптивность — при потере дронов система автоматически перестраивается
Устойчивость — даже при выходе 30% дронов из строя группа продолжает движение
В коде выход из строя моделируется простым механизмом отказов:
def simulate_failure(self):
for drone in self.drones:
if drone.active and random.random() < self.failure_rate:
drone.active = False
Визуализация: наблюдаем за происходящим
Класс Visio позволяет в реальном времени наблюдать ход моделирования:
class Visio:
def __init__(self, swarm):
self.swarm = swarm
# Настройка визуализации
self.fig, self.ax = plt.subplots(figsize=(12, 8))
self.ax.set_xlim(-20, 20)
self.ax.set_ylim(-20, 20)
self.ax.set_title("Рой дронов: автономное перестроение")
self.ax.set_xlabel("X")
self.ax.set_ylabel("Y")
self.drone_dots = self.ax.plot([], [], 'bp',
markersize=8,
alpha=0.6,
label='Активные дроны')[0]
self.failed_dots = self.ax.plot([], [], 'ks',
markersize=4,
alpha=0.3,
label='Потерянные дроны')[0]
self.obstacle_dots = self.ax.plot(
[o[0] for o in swarm.obstacles],
[o[1] for o in swarm.obstacles],
'rx', markersize=10, label='Опасный район'
)[0]
self.target_dots = self.ax.plot([0], [0], 'gx',
markersize=10,
label='Целевой район')[0]
self.ax.legend()
self.ani = FuncAnimation(self.fig,
self.animate,
frames=2000,
init_func=self.start,
blit=True,
interval=1)
def start(self):
self.drone_dots.set_data([], [])
self.failed_dots.set_data([], [])
return self.drone_dots, self.failed_dots
def animate(self, frame):
self.swarm.update()
active_x, active_y = [], []
failed_x, failed_y = [], []
for drone in self.swarm.drones:
if drone.active:
active_x.append(drone.x)
active_y.append(drone.y)
else:
failed_x.append(drone.x)
failed_y.append(drone.y)
self.drone_dots.set_data(active_x, active_y)
self.failed_dots.set_data(failed_x, failed_y)
return self.drone_dots, self.failed_dots
self.swarm - объект класса Swarm
self.swarm.update() - метод, реализует логику трех правил, описанных выше.
На анимации вы увидите, как:
Дроны самоорганизуются из хаотичного облака в структурированную группу
Группа обтекает препятствия без централизованного планирования
Потерянные дроны (черные квадраты) остаются на месте, а живые продолжают движение


Практическое применение
Описанный подход не просто академическое упражнение. Он может применяться в:
Сельском хозяйстве — рои дронов для мониторинга полей
Поисково-спасательных операциях — покрытие больших территорий
Логистике — доставка грузов группами дронов
Охрана и наблюдение — наблюдение на объекте с подвижных камер
Что можно улучшить?
Наша симуляция — лишь первый шаг. В реальных системах нужно учитывать:
Коммуникационные задержки — в реальности информация передается не мгновенно
Ограниченный обзор — дроны «видят» не идеально
Энергетические ограничения — время автономной работы
Динамические препятствия — движущиеся объекты
Заключение
Роевой интеллект демонстрирует удивительный принцип: сложное поведение не требует сложного управления. Простые правила, выполняемые на локальном уровне, создают робастные системы, устойчивые к сбоям и адаптивные к изменениям.
Код из статьи — упрощенная иллюстрация, но он позволяет уловить суть подхода. Главное — не конкретные коэффициенты (их нужно подбирать под задачу), а сам принцип децентрализованного управления.
А вы сталкивались с роевыми системами на практике? Делитесь опытом в комментариях!
Комментарии (7)

aax
24.11.2025 07:25Python, при всем его удобстве, да пригоден лишь для симуляции. Но никак для выполнения критичных по времени задач в системах реального времени, тем более с железом в виде типичного одноплатника на дроне.

MAXH0
24.11.2025 07:25Забавное приложение:
«Системы оружия двадцать первого века, или Эволюция вверх ногами»хотя начинать стоит, конечно же с «Непобедимый»
Но я настоятельно рекомендую к прочтению в нынешних реалиях именно "Системы..."

VAF34
24.11.2025 07:25Хотелось бы поиграть на своем ПК, но показаны только фрагменты. Класса Swarm не увидел.

ncix
24.11.2025 07:25сложное поведение не требует сложного управления.
Верно, но сложное поведение само по себе не создает способности к решению сложных задач.
Wizard_of_light
Клеточные автоматы на физическом железе.