Split Learning
Разделённое обучение делит нейронную сеть на уровне слоя-разреза: клиенты хранят исходные данные и ранние слои, а сервер обучает остальную часть сети на основе их активаций.
Разделённое обучение — метод совместного распределённого обучения, при котором нейронную сеть делят на выбранном слое между владельцем данных (клиентом) и сервером. Клиент запускает слои до точки разделения на своих приватных данных и отправляет только получившиеся активации, иногда называемые раздробленными данными; сервер запускает оставшиеся слои, вычисляет функцию потерь и отправляет градиент в точке разделения, чтобы клиент мог обновить свои слои. Исходные обучающие данные не покидают клиента, и ни у одной из сторон нет полной модели. Октобрист Гупта и Рамеш Раскар из MIT Media Lab представили этот метод в октябре 2018 года в работе Распределённое обучение глубокой нейронной сети между несколькими агентами. В продолжении, опубликованном в декабре 2018 года, — «Разделённое обучение для здравоохранения» — группа предложила конфигурации, позволяющие больницам совместно обучать модели на разных типах данных пациентов, например снимках для анализа медицинских изображений, не обмениваясь исходными записями.
Как работает разделённое обучение#
На каждом шаге обучения данные дважды пересекают точку разделения: активации передаются от клиента серверу во время прямого прохода, а градиент функции потерь относительно этих активаций возвращается при обратном распространении ошибки. Поскольку для продолжения по правилу цепочки нужен только этот градиент, обновления клиента совпадают с обновлениями при обучении неразделённой модели. Однопроцессная симуляция в PyTorch показывает этот обмен:
import torch
from torch import nn
torch.manual_seed(0)
client = nn.Sequential(nn.Linear(784, 256), nn.ReLU()) # слои до точки разделения рядом с приватными данными
server = nn.Sequential(nn.Linear(256, 10)) # слои после точки разделения
images, labels = torch.randn(32, 784), torch.randint(0, 10, (32,))
# Клиент: прямой проход до слоя разделения, затем отправка только активаций
activations = client(images)
received = activations.detach().requires_grad_()
# Сервер: завершение прямого прохода и обратное распространение ошибки до точки разделения, затем отправка градиента обратно
nn.functional.cross_entropy(server(received), labels).backward()
# Клиент: продолжение обратного распространения ошибки с полученным градиентом
activations.backward(received.grad)
split_grad = client[0].weight.grad.clone()
# При выполнении того же шага на неразделённой модели клиент получает идентичные градиенты
client.zero_grad()
nn.functional.cross_entropy(server(client(images)), labels).backward()
print("Same client gradients as unsplit training:", torch.equal(split_grad, client[0].weight.grad))Выводится Same client gradients as unsplit training: True. Затем каждая сторона выполняет шаг собственным оптимизатором. При наличии нескольких клиентов исходный протокол обучает их по очереди: каждый получает последние веса клиентской части, созданные предыдущим клиентом.
Конфигурация меняется в зависимости от того, что нужно сохранить в тайне. В базовом варианте выше серверу отправляются метки, в U-образном варианте последние слои и метки тоже остаются у клиента, а вертикальный вариант подходит организациям, которые хранят разные признаки для одних и тех же записей:
Разделённое обучение и федеративное обучение#
Федеративное обучение тоже позволяет хранить данные на устройствах их владельцев, но каждый клиент обучает полную копию модели и отправляет обновления весов для усреднения. При разделённом обучении вместо этого отправляются активации и градиенты, поэтому клиентам нужно гораздо меньше вычислительных ресурсов, а полной модели у них нет. При этом объём обмена данными зависит от объёма данных, а не от размера модели, и клиенты обучаются по очереди, а не параллельно. SplitFed, предложенный Чандрой Тхапой и коллегами в 2020 году, сочетает эти два подхода: слои на стороне клиентов запускаются параллельно и усредняются по федеративной схеме.
Вертикальное разделённое обучение также подходит для финансовой отрасли: банк и партнёр, хранящие разные признаки для одних и тех же клиентов, обучают одну модель, как в руководстве SecretFlow по банковскому маркетингу, не обмениваясь приватными данными. Параллелизм по конвейеру аналогичным образом делит сеть по глубине, но распределяет её между GPU одного доверенного кластера, чтобы вместить в память большую модель.
Риски для приватности#
Активации и градиенты по-прежнему содержат информацию о данных. Активации ранних слоёв можно инвертировать и восстановить узнаваемые изображения, а если сервер хранит метки, отправляемые им градиенты могут раскрыть их клиенту. На конференции ACM CCS 2021 Дарио Пасквини, Джузеппе Атенизе и Массимо Бернаски показали, что злонамеренный сервер может перехватить управление обучением с помощью отправляемых градиентов и направить слои клиента так, чтобы сервер мог восстановить приватные входные данные. Защита добавляет шум с помощью дифференциальной приватности, ограничивает объём информации о входных данных, раскрываемой активациями, или выявляет необычные градиенты. Каждый из этих способов может снизить точность. При развёртывании разделённое обучение сочетают с мерами защиты данных, такими как аутентификация и шифрование трафика, поскольку сам протокол регулирует только то, что пересекает точку разделения.
Выбор слоя разделения#
Слой разделения задаёт баланс между вычислениями на клиенте, объёмом трафика и риском раскрытия данных. Раннее разделение требует меньше вычислений на клиенте, но приводит к передаче больших активаций, похожих на входные данные. При более позднем разделении передаются более абстрактные карты признаков, но требуется более мощное клиентское оборудование, что важно для устройств периферийного ИИ. Пропускающие связи усложняют выбор, поскольку нужно отправлять каждый тензор, пересекающий точку разделения. Если разделить Ultralytics YOLO26 после основной сети, придётся передавать три карты признаков, поскольку конфигурация модели подаёт выходы слоёв 4, 6 и 10 в neck. Для YOLO26n с imgsz=640 они содержат 1 126 400 значений — почти столько же, сколько 1 228 800 значений во входном изображении.










