Игру написала нейросеть: как это сделано
Обычно под «создать игру нейросетью» понимают генерацию: описал словами — получил картинки, уровни, текст. Здесь было другое. Контента в арене нет вовсе: каждое поколение считается из предыдущего. ИИ написал не контент, а работающую систему — сервер, который держит общий мир, разбирает спор колоний за каждую клетку и переживает перезапуски.
Что получилось, в цифрах
- движок — 1 125 строк кода без комментариев: шаг мира на numpy, поле 320×180 клеток, замкнутое в тор, владение каждой клетки и смотритель;
- скорость — один шаг мира 0,41 мс при одной колонии и 17,5 мс при сорока семи; арена идёт 14 шагов в секунду непрерывно, а не считается по запросу;
- цена трансляции — полный кадр поля весит 3 937 байт в сжатом виде, но зрителю обычно уходит разница с его прошлым кадром, в среднем 1 278 байт: 12,5 КБ/с на зрителя вместо 38,4;
- мест под колонии — 50, цвета считаются по золотому углу 137,5°, поэтому два соседних оттенка не путаются.
Шесть переделок, и каждая — из-за того, что мир вставал
Главная трудность оказалась не в коде шага, а в том, что мир должен кончаться. Арена обязана умереть, чтобы началась следующая, — и каждый раз находился способ не умереть:
- бессмертные колонии. Колония с правилом B3/S012345678 за 181 поколение не изменилась ни на одну клетку: 37 532 живых пикселя до и столько же после. В списке выживания зажжены все цифры, значит клетка не умирает никогда, а расти ей некуда — вечный тупик, в котором ни вымирания, ни зарастания;
- захват без зарастания. Арена №9 простояла 7 034 поколения: колония Репликатора владела всем живым, а это правило держит ровно половину поля и порог «заросло» не берёт никогда. Выяснилось, что условие конца мерило заполненность поля вместо доли живого — не то, что собирались мерить;
- рябь и окаменение. Их приносят игроки: из 400 случайных правил половина даёт рябь (всё мерцает, ничего не растёт), 6 % вымирают сразу. Двадцать тысяч застывших пикселей плюс пятнадцать тысяч мерцающих — и ни одно условие конца не срабатывает.
Половина работы — замеры, а не код
Интереснее другое: почти каждая догадка была неверной, и это выяснялось прогоном, а не рассуждением. Вот снятые — свои же:
- «Запретим неубиваемые правила по списку S от 4 до 8». Замер на квадрате из 900 клеток за 200 шагов показал, что такой критерий ложно запрещает Коралл — тот клетки теряет. Правильная граница: зажжены все цифры от 1 до 8;
- «Отберём неинтересные правила по заполнению поля». Первая версия ворот отбраковала саму игру «Жизнь». Мерить пришлось не заполнение, а оборот — долю живых клеток, сменившихся за шаг: у Жизни он 0,88, у ряби выше 0,8 при заполнении больше 15 %, у окаменения ниже 0,02 при заполнении больше 30 %;
- «Новичку поможет воронка — расчистим место от удара». Не помогла ни при 16×16, ни при 64×64: в захваченном мире новая колония гибла при любой. Сработало другое — фора молодой колонии на первые 150 поколений;
- «Красивая симметричная фигура живёт лучше». Наоборот. Замер на сорока фигурах: четырёхкратно симметричная живёт медиану 4 поколения (14 из 40 гибнут дотла) против 62 у той же фигуры со сломанной симметрией. Игра «Жизнь» сохраняет симметрию, поэтому симметричная фигура обречена складываться в себя. Теперь генератор нарочно портит симметрию на одну шестую клеток;
- «Это будет дёшево — процентов двадцать ядра». Оказалось 58 % одного ядра при 43 колониях: прикидку делали на ноутбуке, а сервер слабее.
Генератор фигур тоже не придуман, а подобран перебором: половина размера 7, плотность 0,45, шум 0,17 дают медиану 892 поколения, а отбор лучшей из четырёх коротким прогоном — 1 228 против 688. Проверка на готовом коде: пятнадцать фигур из браузера, медиана 1 506 поколений, ни одна не вымерла дотла.
Чем это отличается от генерации
Генерация отвечает на вопрос «как это выглядит». Здесь приходилось отвечать на вопрос «что случится через тысячу шагов», а на него нельзя ответить, не запустив: игра «Жизнь» тьюринг-полна, поэтому судьба узора алгоритмически неразрешима. Отсюда и устройство работы: гипотеза — прогон — цифра — правка. Код писал ИИ, но решения вроде «пусть арена гибнет, не подсеивать» принимал человек, и спор шёл именно о них.
Бросить свою колонию