Диффузионные модели
Регрессия выдаёт среднее из показанных ответов. Когда правильных ответов два, среднее неправильно: робот едет между двумя объездами прямо в чайник. Нужна модель, которая выдаёт один из правильных ответов. В этом уроке разбираем такую модель — диффузионную. Она учится убирать шум из данных, а генерирует наоборот: начинает с чистого шума и шаг за шагом приближается к данным. Всё показываем на точках на плоскости: две спирали, шум, сеть-денойзер и обратный путь. Если диффузия знакома, урок можно пропустить.
Генератор вместо одного ответа
Политика, обученная по среднеквадратичной ошибке, выдаёт среднее из показанных действий. Если оператор объезжал чайник то слева, то справа, среднее из двух объездов ведёт прямо в чайник. Так устроена сама ошибка: её минимум — среднее всех правильных ответов, и больше данных этого не меняет.
В уроке 1.3 мы обходили среднее двумя способами. Смесь гауссиан выбирает один из нескольких вариантов, но их число нужно знать заранее, и каждый вариант — простое пятно. Бины делят каждую координату на интервалы, но независимые бины теряют связь между координатами, а общих бинов для многих координат нужно слишком много.
Поэтому нужна модель, которая выдаёт сэмпл — случайный пример из распределения данных любой формы. Такую модель называют генератором. Запустишь её дважды и получишь два разных ответа, и оба будут похожи на данные: один объезд слева, другой справа.
Разберём генератор на самых простых данных — точках на плоскости. Они лежат на двух спиралях, по 1000 точек на каждой. Спирали играют роль двух объездов: хороший генератор кладёт точки на спирали, на обе поровну, и не кладёт между витками. Опорные работы урока — DDPM (Ho, Jain, Abbeel, 2020) и DDIM (Song, Meng, Ermon, 2021).
Случайный шум получить легко: это стандартная функция любой библиотеки. Как превратить шум в точку на спирали?
Путь от данных к шуму
Превратить шум в точку на спирали за один шаг трудно: сеть, которую учат такому превращению по среднеквадратичной ошибке, снова выдаёт среднее. В лаборатории это будет видно на опыте.
Поэтому идут маленькими шагами и начинают с обратного направления, от данных к шуму. Оно простое: на каждом шаге точка немного сжимается к центру, и к ней добавляется немного гауссова шума. За шагов от спиралей остаётся гауссово облако. Этот путь фиксирован, учить его не нужно. Сколько шума добавить на шаге , задаёт расписание. В DDPM оно линейное: доля шума растёт от 0,0001 на первом шаге до 0,02 на последнем.
За ходом процесса удобно следить по одному числу — , доле сигнала, которая осталась от исходной точки к шагу . В начале , точка чистая; к концу почти ноль. Любую точку можно зашумить сразу до любого шага, не проходя промежуточные.
Сначала нарисуй, как, по-твоему, падает на линейном расписании, а облако слева подскажет, сколько сигнала осталось на шаге . Потом сравни прогноз с настоящей кривой и с косинусным расписанием из Improved DDPM (Nichol, Dhariwal, 2021).
Под капотом: прямой процесс и два расписания
Шаг прямого процесса в нотации DDPM:
Последняя строка и позволяет зашумить точку сразу до шага . Линейное расписание DDPM: растёт от до 0,02 за шагов. Отсюда и — это наш расчёт по формулам статьи. Сами авторы DDPM оценивают, что отличается от гауссова шума на бит на измерение.
Косинусное расписание из Improved DDPM задают сразу через :
Отсюда , сверху её ограничивают значением 0,999. У этого расписания .
Как считается ошибка прогноза. Прогноз хранится в 41 точке, через каждые 25 шагов. Ошибка — среднее расстояние по вертикали между прогнозом и настоящей кривой линейного расписания в этих точках.
Итак, линейное расписание теряет сигнал быстро: к середине пути его остаётся меньше десятой, а последнюю треть пути точки почти неотличимы от шума. Путь от данных к шуму мы знаем точно. Как пройти его обратно, от шума к спиралям?
Куда сдвигать точку на обратном пути
Чтобы пройти путь обратно, на каждом шаге нужно знать, куда сдвинуть зашумлённую точку, чтобы она стала больше похожа на данные. Это трудно: зашумлённая точка могла прийти из многих мест, и чем сильнее шум, тем больше вариантов. Если на каждом шаге двигать её к среднему всех вариантов, она придёт в центр, между спиралями. Это та же ошибка, что у регрессии.
Выход — на каждом шаге спрашивать денойзер: он оценивает, откуда пришла зашумлённая точка. Если знать все обучающие точки, лучшая оценка — их среднее с весами. Чем ближе обучающая точка, тем больше её вес, а насколько быстро вес падает с расстоянием, зависит от уровня шума. Стрелка от точки к оценке показывает направление к данным. Поле таких стрелок называют score; в статье EDM (Karras et al., 2022) это «a vector field that points towards higher density of data at a given noise level».
На сцене генерация, которую ведёт идеальный денойзер: он знает все 2000 точек, сети здесь нет. Перематывай генерацию по шагам. Оранжевые точки — 300 сэмплов на этом шаге, стрелки показывают, куда денойзер тянет точки сцены. Пробную точку можно перетаскивать: крестик — её оценка, подсвечены обучающие точки, которые денойзер усредняет.
Под капотом: идеальный денойзер и score
В нотации EDM точку зашумляют так: , . Для конечной выборки оптимальный денойзер и score выражаются в замкнутой форме:
Шаг DDPM соответствует уровню шума , если поделить на . В конце пути , в начале — около 160. Score в нотации DDPM связан с предсказанным шумом:
Значит, сеть, которая предсказывает шум, заодно знает направление к данным. Score — градиент по входу , а не по параметрам сети.
Выход — взвешенное среднее обучающих точек, поэтому такой денойзер может только воспроизводить данные (EDM, приложение B.3, ур. 57; Gu et al.). К этому вернёмся в разделе про память.
Как устроена сцена. Генерация — DDIM на 50 шагах, 300 точек из одного и того же шума, моменты шагов . Стрелки стоят в узлах сетки 15 × 15 с шагом 0,3 и показывают направление от узла к оценке денойзера на текущем шаге. Стрелка смотрит в среднее, если отклоняется от направления на центр масс данных меньше чем на 15°; узлы ближе 0,3 к центру не считаем. Стрелка ведёт к ближайшей спирали, если отклоняется от направления на ближайшую точку данных меньше чем на 30°; считаем узлы внутри круга радиусом 1,75, где лежат спирали, и не ближе 0,08 к данным.
Выходит, в начале генерации денойзер тянет все точки к центру, в конце — к ближайшему витку, а между этими этапами точка выбирает спираль. Но идеальный денойзер хранит все 2000 точек и на каждом шаге перебирает их все. Можно ли получить те же стрелки от сети, которая данных не хранит?
Диффузия на двух спиралях
Можно: денойзер заменяют сетью, которая учится по примерам и данных не хранит. Для картинок и действий робота иначе нельзя: примеров миллионы, перебирать их на каждом шаге слишком долго. Обучение идёт в твоём браузере и занимает секунды.
Сеть учится так: берём точку спирали, случайный шаг и случайный шум, зашумляем точку сразу до шага и просим сеть угадать добавленный шум. Ошибка — средний квадрат разницы между настоящим и предсказанным шумом. В статье DDPM её называют . Предсказывать шум удобно: он всегда одного масштаба, а по шуму легко вычислить оценку чистой точки, то есть ту же стрелку, что в разделе 3.
Генерация идёт в обратную сторону: берём точку гауссова облака и идём от к нулю. На каждом шаге сеть предсказывает шум, мы убираем его часть, и точка становится на шаг ближе к данным. DDPM на каждом шаге добавляет ещё и немного свежего шума, поэтому путь случайный. DDIM берёт ту же обученную сеть, но шагает без свежего шума, и путь от старта до финиша детерминирован.
В лаборатории ты обучишь сеть и сравнишь её с регрессией «шум → точка». Найдёшь, сколько шагов нужно DDPM и DDIM, и границу, за которой соседние стартовые точки уходят на разные спирали.
Под капотом: сеть и обучение
- Вход. Координаты точки, 16 пар синусов и косинусов от случайных проекций координат (признаки Фурье: с ними сеть быстрее схватывает мелкие детали) и вложение номера шага: и синусы-косинусы на пяти частотах. Всего 45 чисел.
- Сеть. Два скрытых слоя по 64 нейрона с активацией SiLU, на выходе два числа — предсказанный шум. Около 7300 параметров. Для сравнения, у DDPM для CIFAR-10 их 35,7 млн.
- Обучение. Adam, пакет 125 примеров, эпоха — проход по 2000 точкам, то есть 16 шагов. Шаг обучения , после 200 эпох , после 400 — .
- Отступление от DDPM. В DDPM номер шага при обучении равномерный. Мы берём чаще маленьким: , где равномерно от 0 до 1. Тонкая структура спиралей видна только при малом шуме, и так сеть учится в несколько раз быстрее.
- Кривая ошибки. Это на фиксированном наборе из 4000 троек с равномерным , как в статье. Мы усредняем ошибку по двум координатам.
- Регрессия «шум → точка». Та же сеть без номера шага. 400 шагов Adam по MSE: на входе случайный шум, на выходе случайная точка данных.
Под капотом: шаги DDPM и DDIM
Шаг DDPM, :
Шаг DDIM с момента на более ранний момент :
При шаг детерминирован, при сэмплер совпадает с DDPM. Осторожно с нотацией: в статье DDIM буквой обозначено то, что в DDPM называется .
Как устроены сэмплеры в лаборатории. Оба — одна формула DDIM, DDPM получается при . Сеть всегда одна и та же, обученная на всех 1000 шагах. Если шагов генерации меньше 1000, берём моменты : у конца пути, где шум мал, шаги чаще. Последний шаг всегда выдаёт оценку без шума. Оценку держим в квадрате от −2,2 до 2,2, как картинкам ограничивают пиксели.
Под капотом: как считаются критерии
- Точка на спирали, если ближайшая из 2000 обучающих точек ближе 0,1. Её спираль и считается спиралью точки. Ширина спиралей в данных — шум со стандартным отклонением 0,05, расстояние между соседними витками около 0,27.
- За окружностью. Пунктирная окружность радиусом 1,14 делит данные пополам: за ней лежит ровно половина обучающих точек. Если сэмплер стягивает облако к центру, за окружностью точек становится меньше.
- Форма держится, если на спиралях не меньше 80% точек, а за окружностью — не меньше 25%.
- Генерация. 1000 точек из одного и того же стартового шума; у DDIM рядом — тот же шум. Траектории рисуем для 40 точек. В миссии про бассейны — DDIM на 20 шагах.
- Карта бассейнов. Из узлов сетки 41 × 41 запускаем DDIM на 20 шагах и красим узел по спирали, на которую пришёл финиш. Узлы, финиш которых не попал на спираль, не красим.
Итак, сеть заменила идеальный денойзер, и генерация кладёт точки на спирали, причём старт решает, на какую. DDIM на той же сети держит форму на 6–8 шагах, где DDPM уже стягивает облако к центру. Роботу же ответ нужен за десятки миллисекунд. Сколько шагов делают настоящие роботы и чем сокращают их число?
Сколько шагов делают роботы
Каждый шаг генерации — полный проход сети. DDPM делает 1000 шагов: модели для CIFAR-10 нужно 17 секунд на пакет из 256 картинок, а роботу ответ нужен за десятки миллисекунд.
Просто взять меньше шагов DDPM не получается. В лаборатории на 6–8 шагах облако стягивалось к центру, и внешние витки пустели: DDPM на крупном шаге заменяет предсказанный шум свежим и теряет направление движения.
Поэтому шагают так, чтобы уже предсказанное не терялось: DDIM на той же сети, решатели вроде DPM-Solver, дистилляция в 1–3 шага или flow matching с прямыми путями. Вот сколько шагов делают модели роботов:
| Модель | Метод | Шагов при выводе |
|---|---|---|
| Diffusion Policy, реальные роботы | DDIM, обучение на 100 шагах | 10; 0,1 с на RTX 3080 |
| UMI, 2024 | DDIM | 16 |
| Consistency Policy, 2024 | дистилляция | 1 или 3; 21 мс против 192 мс у DDIM на 15 шагах |
| Octo, 2024 | DDPM | 20 |
| RDT-1B, 2025 | DPM-Solver++ | 5 вместо 100 |
| π0, 2025 | flow matching | 10; 73 мс на RTX 4090 |
| GR00T N1, 2025 | flow matching | 4; 63,9 мс на L40 |
| π0.7, 2026 | flow matching | 5 |
Осторожно: в конфигах репозитория Diffusion Policy по умолчанию стоит 100 шагов, а не 10. Для картинок порядок такой же. На CIFAR-10 DDIM за 50 шагов даёт FID 4,67 против 4,04 за 1000, DPM-Solver — 4,70 за 10 вызовов сети, EDM с условием на класс — 1,79 за 35, consistency models — 3,55 за один шаг. Чем меньше FID, тем ближе картинки к настоящим.
Flow matching при гауссовом шуме на входе эквивалентен диффузии: сэмплер DDIM совпадает с методом Эйлера для flow matching. А rectified flow учит прямые пути от шума к данным, и шагов нужно ещё меньше. Это урок 1.8.
Под капотом: мост к flow matching
Во всём курсе для flow matching время идёт от шума к данным: — шум , — данные , как в статье π0. Точку на пути и цель обучения записывают так:
Сеть учит скорость , а генерация — это движение по ней от к . Обрати внимание: в DDPM время направлено наоборот, — данные, — шум. В коде openpi шум тоже стоит при : x_t = t * noise + (1 - t) * actions, и интегрируют с шагом dt = -1/10. Подробно — в уроке 1.8.
Генератор стал быстрым, но пока выдаёт любую правдоподобную точку. Роботу же нужно действие для конкретной ситуации. Как заставить генератор выдать то, что заказали?
Генерация по заказу
Генератор выдаёт любую точку данных, а роботу нужна не любая: действие должно подходить к тому, что видит камера. В нашем примере заказ — номер спирали: «дай точку на спирали 1».
Самое простое — подать условие сети на вход: при обучении сеть видит номер спирали каждой точки. Это работает не до конца: без усиления часть точек ложится не на ту спираль или между витками. Сколько таких точек, проверишь ставкой в опыте ниже.
Усилить условие без отдельного классификатора позволяет classifier-free guidance (Ho, Salimans, 2022). Одну сеть учат сразу двум задачам: при обучении условие иногда выбрасывают, с вероятностью 0,1–0,2, и сеть умеет предсказывать шум и с условием, и без. При генерации берут оба предсказания и сдвигают ответ дальше от безусловного. Насколько дальше, задаёт вес .
Сеть для опыта такая же, как в лаборатории, плюс вход «номер спирали». Её обучение начнётся, когда раздел появится на экране, и займёт несколько секунд. Каждая генерация ставит точку на график: по вертикали точность — доля точек на заказанной спирали, по горизонтали покрытие — доля точек этой спирали, рядом с которыми оказалась хоть одна сгенерированная.
Под капотом: classifier-free guidance
Здесь — условие, — пустое условие. При это обычная условная модель. В статьях вес записывают по-разному: если формулу пишут как , то .
В опыте: та же сеть, что в лаборатории, плюс два входа «номер спирали»; если условие выброшено, оба равны нулю. Вероятность выбросить условие 0,2 — у Ho и Salimans значения 0,1 и 0,2 работают одинаково. 3000 шагов Adam. Генерация — DDIM на 20 шагах, 500 точек из одного и того же шума. Точность — доля сгенерированных точек, у которых ближайшая обучающая точка ближе 0,1 и лежит на заказанной спирали. Покрытие — доля точек заказанной спирали, рядом с которыми, ближе 0,1, есть сгенерированная точка.
Real-Time Chunking тоже использует guidance, но другой: на каждом шаге добавляет к полю скоростей градиентный член, чтобы новый чанк согласовывался с уже исполняемым.
Получается, что guidance делает генерацию точнее, но беднее, и при большом весе точки сбиваются в немногие места спирали. Крайний случай бедности — модель, которая только повторяет обучающие примеры. Бывает ли так с диффузией?
Память или обобщение
Бывает. Генератор полезен, когда создаёт новые примеры, похожие на данные, а модель, которая только повторяет обучающие примеры, — это таблица поиска.
Почему так бывает? Идеальный денойзер из раздела 3 оценивает чистую точку как взвешенное среднее обучающих точек. Если пройти с ним генерацию до конца, каждая точка придёт ровно в одну из обучающих. А сеть мы учим приближать именно его.
Спасает то, что сеть не может и не успевает запомнить всё. Пока она учится недолго, она выучивает гладкую форму распределения и кладёт точки между обучающими. На маленькой выборке и при долгом обучении сеть постепенно переходит к копированию.
Слева от шторки идеальный денойзер, справа маленькая сеть, обе на одних и тех же точках со спиралей. Копией считаем сэмпл, который ближе 0,02 к одной из обучающих точек. Двигай шторку, меняй N и шаг обучения.
Под капотом: как считается доля копий
Сеть та же, что в лаборатории, учится 8000 шагов на пакетах по 64 примера. Каждые 1000 шагов генерируем 300 точек DDIM на 50 шагах из одного и того же шума и считаем, какая доля из них ближе 0,02 к обучающей точке. Идеальный денойзер генерирует тем же сэмплером. Если взять свежие точки со спиралей, а не сэмплы, «копиями» случайно оказалось бы меньше 6% даже при : так мы проверили, что порог 0,02 не путает новые точки с копиями.
Для больших моделей известно следующее. Carlini et al. нашли 109 копий обучающих картинок среди 175 млн генераций Stable Diffusion, а из моделей на CIFAR-10 извлекли 1280 картинок — 2,5% датасета. Главный фактор — дубликаты в данных, и диффузия запоминает больше, чем GAN. Kadkhodaie et al. показали, что при две сети, обученные на непересекающихся данных, генерируют почти одинаковые картинки. Bonnaire et al.: время до обобщения не зависит от размера выборки, а время до запоминания растёт с ней линейно, поэтому остаётся окно для ранней остановки.
Итак, идеальный денойзер только копирует, а сеть копирует на малых данных и при долгом обучении. Для робота это значит, что на десятке демонстраций диффузионная политика может повторять записанные движения вместо того, чтобы обобщать. Какие ещё заблуждения о диффузии встречаются чаще всего?
Восемь частых заблуждений
К каждому вопросу сначала выбери, насколько уверенно отвечаешь, потом сам ответ. В конце увидишь не только число верных ответов, но и калибровку: совпадает ли твоя уверенность с тем, как часто ты прав.
Итоги урока
- Прямой процесс фиксирован: шум добавляют по расписанию. К концу линейного расписания от сигнала остаётся , а последнюю треть пути точки почти неотличимы от шума.
- Сеть учится предсказывать добавленный шум. Ошибка выходит на плато выше нуля: часть шума угадать нельзя в принципе.
- Денойзер указывает к данным: при сильном шуме — к среднему, при слабом — к ближайшей спирали. Поэтому сэмпл приходит в одну из мод, а не в их среднее.
- DDIM — та же сеть с детерминированными шагами. Поэтому у роботов 4–16 шагов вывода, а не 1000.
- Classifier-free guidance — одна сеть, условие при обучении иногда выбрасывают. Сильный guidance меняет разнообразие на точность.
- Идеальный денойзер только копирует. Сеть на малых данных и при долгом обучении начинает копировать обучающие примеры.
Осталась одна проблема. Мы генерировали отдельные точки на плоскости, и условием был номер спирали. Роботу нужно другое: пачка действий на несколько шагов вперёд, согласованная во времени, а условие — картинка с камеры. Если генерировать каждое действие отдельно, соседние действия могут выбрать разные объезды. Как превратить диффузию в политику, которая выбирает один объезд и держится его, разберём в уроке 1.5.
Открытые вопросы
Почему диффузионная политика на десятке демонстраций может вести себя как таблица поиска и чем это плохо для робота?
На малых данных денойзер близок к идеальному: оценка чистого действия — взвешенное среднее обучающих примеров, и генерация приходит в одну из записанных траекторий. В препринте 2505.05787 Diffusion Policy на малых датасетах выдавала траекторию из обучения даже на фото кошки, а простая таблица поиска работала не хуже при 0,0034 времени вывода. Для робота это значит, что новых движений он не придумает: в незнакомой сцене он повторит ближайшую демонстрацию, даже если она там не подходит.
Робот должен реагировать за 20 мс. Какие способы сократить число шагов ты знаешь и чем каждый платит?
DDIM и решатели вроде DPM-Solver берут ту же сеть с меньшим числом шагов, но на очень малом числе шагов теряют качество, как в лаборатории. Дистилляция и consistency-модели сводят вывод к 1–3 шагам (Consistency Policy — 21 мс против 192 мс у DDIM на 15 шагах), но нужна отдельная дорогая стадия обучения. Flow matching с прямыми путями даёт 4–10 шагов (урок 1.8). Можно не ждать вывода: исполнять пачку действий и считать следующую асинхронно, как Real-Time Chunking. Одношаговые головы быстрее всего, но заметно теряют в успешности: в техотчёте одного автора drifting-голова для GR00T ускорила голову с 45 до 5 мс ценой падения успешности.
Гид по статье
J. Ho, A. Jain, P. Abbeel, «Denoising Diffusion Probabilistic Models», NeurIPS 2020.
- Читать внимательноКак устроен прямой процесс и почему получается из за один шаг; параметризацию через шум и цель (уравнение 14); параллели с denoising score matching и динамикой Ланжевена.
- Можно пропуститьПодробные выкладки вариационной оценки и детали архитектуры сети для картинок.
- Вопрос по ходуСколько вызовов сети нужно, чтобы сгенерировать одну картинку, и почему авторы взяли именно ?
Материалы
- Хендбук Яндекса по машинному обучению, глава 8.5Диффузионные модели на русском
- L. Weng, What are Diffusion Models?Обзор с выкладками и нотацией DDPM
- Y. Song, Generative Modeling by Estimating Gradients of the Data DistributionВзгляд через score
- S. Dieleman, Guidance: a cheat code for diffusion modelsClassifier-free guidance подробно
- Welch Labs для 3Blue1Brown, 2025Видео о том, как работают диффузионные модели
- MIT 6.S184Курс MIT о диффузии и flow matching, конспект — arXiv 2506.02070
- tiny-diffusionНебольшая реализация диффузии на двумерных данных
- Diffusion literature for roboticsСписок работ о диффузии в робототехнике
Дальше: Diffusion Policy. Заменим точки на пачку действий, а условием сделаем наблюдение камеры. Тогда начальный шум выберет, объедет робот чайник слева или справа, а денойзинг доведёт объезд до конца — урок 1.5 «Diffusion Policy».