Миналият петък отбеляза пускането на Unity 5.3.5p7, малка корекция, която премина без предупреждение или шум. В този пач обаче има точка, сгушена сред множеството други поправки, която заслужава много повече внимание.

Това е вярно. Оптимизирането на вашето време за компилиране се завърна!* След надстройката времето ми за компилиране премина от приблизително 17 секунди на 6,3 секунди.

*(След Unity 5.2.4 повечето версии имат бъг на компилатора, който отрича най-ефективната стратегия за оптимизиране на времето за компилиране)

Но не съм тук само, за да опиша колко невероятно е да чакате 10 секунди по-малко всеки път, когато правите промяна на кода, тук съм, за да попитам: Защо повече хора не са развълнувани да видят отстраняването на тази грешка? Мисълта за намалено време за компилиране не предизвиква ли радост у другите?

Единственото ми заключение е, че повечето хора не осъзнават, че могат да оптимизират времето за компилиране. Няма официална документация и съответните публикации във форума са остарели, така че получаването на голямата картина не е лесно. Но след като имате това, намаляването на времето за компилиране е лесно и ползите са огромни.

И така, ето моята лична стратегия за борба с времето за компилиране:

1. Вземете фактите

Първо трябва да разберете колко време отнема компилирането на вашия код. За моята собствена кодова база от един човек тя се движи около 17 секунди. За по-големи екипи справедливата оценка би била около 30 секунди. За да го представя в перспектива, правя около 20–30 промени на час и трябва да чакам 30 секунди вместо 6,3 секунди, което би добавило около допълнителни 10 минути чакане към моя график на час.

Представете си колко се натрупва това през деня. През цялата седмица. Всеки месец. След това умножете това число по броя на хората в екипа. И не става въпрос само за загубеното време: по-дългото време за компилиране означава, че е много по-вероятно да се разсеете и да започнете да проверявате имейла или Facebook.

Но първо трябва да знаете времето за компилиране. И искате винаги да го следите, така че да не проверявате нищо, което драстично го увеличава. Спомняте ли си цялото загубено време? За да разреша това, написах разширение за редактор, което можете да изтеглите от моя Github тук.

2. Оптимизирайте!

Преди да оптимизираме, позволете ми да ви дам малко информация за това как работи всичко това. В момента, в който направите промяна на кода, Unity прекомпилира вашия код в .dll (компилиран код), наречен Assembly-CSharp.dll (или Assembly-UnityScript и т.н., ако не пишете на C#).

За да намалите времето, необходимо за повторно компилиране, можете да използвате специални папки, които Unity компилира в отделен .dll, наречен Assembly-CSharp-firstpass.dll. Ключовата част е, че кодът в този .dll няма да се прекомпилира, ако не го промените. Тези специални папки се наричат ​​Добавки и Стандартни активи и трябва да съществуват в директорията от най-високо ниво под Активи.

Неща за отбелязване:

  • Поради реда, в който са компилирани тези .dll, кодът в този firstpass.dll няма да може да препраща към код извън него.
  • Промяната на кода вътре в специалните папки ще прекомпилира и двете .dll и ще отхвърли всички печалби от оптимизацията.

Имайки това предвид, най-добрите кандидати за оптимизация са секции от код, които не зависят от друг код и е малко вероятно да се променят. Активите на трети страни са перфектни. Други части от вашата кодова база също може да има смисъл да се оптимизират.

Въпреки това открих проблем с простото плъзгане и пускане на всички мои активи на трети страни в папката Plugins. Някои от тези активи зависят от техните ресурси, които се намират в първоначалния им импортиран път и се повреждат ужасно, когато това не е така. Така че, за да си спестя време, купих Mad Compile Time Optimizer ($15)***, защото той оставя некодираните файлове там, където са, и също така идва с хубава функция за връщане.

*** Не съм свързан с Mad Compile Time Optimizer по никакъв начин.

3. Вижте други заподозрени

Сега, след като вашите активи на трети страни са оптимизирани, трябва да видите огромно намаляване на времето за компилиране. Това обикновено е мястото, където хората спират, но все още има няколко места, където можем да проверим за повишаване на производителността.

Атрибутът [InitializeOnLoad] е едно такова място. За тези, които не са запознати, InitializeOnLoad е атрибут на Unity, който може да се добави към всеки клас, така че статичният конструктор да бъде извикан при стартиране на редактора (или при завършване на компилацията). Всеки неефективен код там може да добави нетривиално количество време към вашето време за компилиране.

След известно експериментиране открих, че да, кодът, който се изпълнява по време на InitializeOnLoad, се брои към общото време за компилиране.

За да анализирам екземпляри на InitializeOnLoad, регистрирах времето от началото до края на всеки статичен конструктор с подозрително изглеждащ код. Повечето екземпляри на InitializeOnLoad бяха безобидни (0,0–0,2s), но попаднах на един клас, който го злоупотребяваше, за да зарежда и кешира ресурси. Промених обидната част от кода на мързеливо кеширане, когато е необходимо, и продължих напред.

Последното нещо, което трябва да проверите, е вашият собствен код. Има ли класове, които не се използват? Вероятно нямате нужда от тях да отнемат време във вашия проект. Не съм измислил добър начин за регистриране на времето за компилиране на клас файл, но като общо правило размерът на файла е добро приближение за сложността.

Визуализацията е най-лесният начин да приоритизирате кои файлове си струва да разгледате. Използвах GrandPerspective (Mac), защото може да филтрира резултатите по персонализирани правила. В крайна сметка направих филтър, който съвпада с имена, завършващи с .cs, и друг за премахване на файлове с пътища, които съдържат „Plugins“ или „Standard Assets“.

Ето как изглеждаше кодовата база на моя проект в края на оптимизацията. Обърнете внимание, че моят личен код е единственият код, който се компилира след промяна!

TL;DR:

Интересувате се от автоматично валидиране на вашата игра за предотвратяване на повредени компилации? Или може би „използване на аниматора като краен автомат“ вместо изграждане на ваша собствена реализация? Вижте другите ми статии!