C все еще широко используется в игровых движках? - PullRequest
14 голосов
/ 31 августа 2010

Название немного неправильное, я имею в виду "C с классами".

Позвольте мне объяснить, недавно я купил книгу ShaderX7, которая поставлялась с облегченной (и старой) копией движка Unigine для одной из статей о технике теневого отображения.

Я копался в коде, когда понял, что, хотя автор использовал C ++ и наследование и все достоинства C ++, большинство, если не весь контент метода, по сути, был кодом в стиле C; например:

int Shader::get_param(const char *name,char *src,String &dest) const {
    char *s = src;
    int size = (int)strlen(name);
    while(*s) {
        if(!strncmp(s,name,size)) {
            if((s == src || strchr("\n\r",*(s - 1))) && strchr(" \t",*(s + size))) {
                src = s;
                s += size;
                dest.clear();
                while(*s && strchr(" \t",*s)) s++;
                while(*s && strchr(" \t\n\r",*s) == NULL) dest += *s++;
                if(dest.isEmpty()) {
                    Log::error("Shader::get_param(): can't get \"%s\" \n",name);
                    return 0;
                }
                memmove(src,s,strlen(s) + 1);
                return 1;
            }
        }
        s++;
    }
    return 0;
}

Я не говорю, что это плохо, это делает работу, и вот что важно, но я больше привык к конструкциям в стиле C ++, с std :: string, векторами и т. Д. ... и я широко использую библиотеки Boost ; так что этот стиль для меня стал сюрпризом.

Действительно ли лучше / быстрее использовать этот вид кода, чем использовать общий, ОО путь?

Попал ли я в ловушку "слишком много абстракции"?

Редактировать: исправлено имя метода, чтобы было понятно, что он делает.

Ответы [ 4 ]

26 голосов
/ 31 августа 2010

Прежде всего, я должен признать, что я не разработчик игр, хотя в прошлом я разработал полностью функциональный движок для 3D-игр.

Кроме того, у меня есть несколько слов об оптимизации, "испорченных" языках и так далее.

При разработке приложения & mdash; любое приложение & mdash; золотое правило оптимизации - «не оптимизируйте, прежде чем заставить его работать». Вы должны полностью поддерживать все функции, которые вы хотите в вашем приложении, и только тогда вы должны оптимизировать его. Причины меняются; наиболее важным является то, что, хотя вы можете верить, что что-то «медленное», это может быть не вашим узким местом. Вы можете тратить много времени на оптимизацию чего-то, что не требует оптимизации. Кроме того, оптимизации часто затуманивают простоту и удобство обслуживания вашего кода, что может привести к ошибкам в ближайшем или отдаленном будущем. Если этот фрагмент кода не требует оптимизации, вы напрасно усложнили код.

Хотя это золотое правило оптимизации, есть одно большое исключение. Когда вы заранее знаете, что ваше приложение будет максимально загружено, вам нужно будет сделать несколько разных выборов в начале (в архитектуре или на этапах проектирования), а также по пути. Кроме того, общее правило, что платформы становятся лучше и быстрее, не относится к играм, где конкуренция между разработчиками находится на самом краю технологии. Вот несколько моментов для рассмотрения:

  1. Некоторые языковые функции могут быть дорогостоящими. Исключения в C ++ являются хорошим примером.
  2. Некоторые языковые функции могут на самом деле сохранить ваш код и будут стоить мало или вообще ничего во время выполнения. Шаблоны C ++ являются хорошим примером, хотя вы все равно можете создать большое количество кода во время компиляции, что приведет к увеличению размера двоичного файла и, следовательно, к снижению производительности, потенциально.
  3. Инфраструктуры (например, STL) являются общими. Принимая решение, специфичное для вашего домена, вы МОЖЕТЕ повысить свою производительность. Простой пример & mdash; если у вас есть вектор, который всегда будет иметь длину 3 элемента, вы определенно будете лучше, чем реализация stl :: vector. Тем не менее, это не всегда так. Для дальнейшего чтения см. Главу 11 «Эффективного C ++» Дов Булька. Это отличная книга в целом по вашему вопросу.

В целом, использование C с классами является хорошим началом для написания быстрого кода, сохраняя при этом структурированный и хорошо спроектированный проект, но не следует пренебрегать всеми отличными возможностями C ++. Чаще всего попытка развернуть собственное решение проблемы, охватываемой C ++ (например, полиморфизм), будет медленнее, чем готовое решение, если только вы не можете сделать решение ОЧЕНЬ специфичным для данной проблемы. .

8 голосов
/ 31 августа 2010

C ++ без STL

Как я видел в своей профессиональной истории, в разработке игр чаще всего используется не C с классами, а C ++ без STL. Некоторые части STL считаются слишком медленными для разумной производительности игрового движка, особенно потоки. Другие части обеспечивают приемлемую общую производительность, но способ распределения памяти в большинстве случаев неприемлем для игр - это применимо к библиотекам строк и векторов в большинстве сценариев. Отличное подробное обсуждение этого можно найти в EASTL white paper . Разработчики игр часто используют boost или даже реализуют собственную альтернативу части STL (см. Game STL или EASTL ).

Без исключений

Существует одна особенность языка, которая никогда не используется в каких-либо критических по производительности деталях двигателя, - обработка исключений. Это связано с тем, что на самой важной платформе для разработки игр (Visual Studio x86 / x64) исключения являются довольно дорогостоящими, и вы платите некоторую стоимость даже в тех случаях, когда исключений нет. Исключения исключаются из-за того, что некоторые платформы консоли разработки даже не предоставляют их, или известно, что поддержка является неполной, ненадежной и в основном «сломанной».

Используется для C

Кроме этого, часто бывает, что игровые программисты используют C вместо C ++ просто потому, что они к этому привыкли.

4 голосов
/ 31 августа 2010

Если вы действительно хотите рисовать графику как можно быстрее, и вы начинаете с того, что говорите

int size = (int)strlen(name);

, что похоже на лай неправильного дерева.* получить?Он не выглядит графическим.

Оптимизация не состоит в том, чтобы делать неправильные вещи очень быстро.Речь идет о сокращении жира и тратить все время на важные вещи.Если ваш графический движок тратит значительное количество циклов на обработку строк, у него есть проблема, которую, вероятно, не решит смена языков.

Итак ... пишите вспомогательные функции как можно быстрее, понятнее и понятнее.Когда вам нужно микрооптимизировать критический путь, C ++ по-прежнему охватывает стиль низкого уровня.

3 голосов
/ 31 августа 2010

Если оно:

  1. Работает, и вы довольны им, не трогайте его.
  2. Не работает, меняйте его так, как вам нравится, покакак это исправлено потом.
  3. Работает и не достаточно быстро, сделайте это быстрее (НЕ без профилирования в первую очередь).

Я предполагаю, что вы попали в случай 1,поэтому я бы посоветовал оставить это в покое.Если вам нужно что-то изменить, и у вас нет серьезных проблем с производительностью, во что бы то ни стало внесите в него некоторые из C ++.В общем случае мне трудно читать программисты на C ++ в стиле C, они либо:

  1. У них не было времени или нет дела, чтобы научиться делать это на C ++ (что на самом деленеприемлемо с точки зрения безопасности),
  2. выбирают те части C ++, которые им действительно нужны (очень мудро),
  3. или им действительно нужны рабочие характеристики C (очень редко).

Глядя на код, это может быть любой из этих случаев.В любом случае, теперь это не имеет значения, код в ваших руках.

...