Расширение макросов C / C ++ противГенерация кода

StackOverflow https://stackoverflow.com/questions/1807617

  •  05-07-2019
  •  | 
  •  

Вопрос

Как расширение макросов, так и генерация кода имеют свои плюсы и минусы.Какой ваш любимый подход и почему?Когда мы должны предпочесть одно другому?Пожалуйста, любезно сообщите.Спасибо!

Расширение макросов может быть очень удобным и полезной:http://dtemplatelib.sourceforge.net/table.htm

против

В то время как генерация кода дает вам много хорошего кода:http://code.google.com/p/protobuf/ http://incubator.apache.org/thrift/

Это было полезно?

Решение

Это компромисс.Позвольте мне привести пример.Я наткнулся на технику дифференциальное исполнение примерно в 1985 году, и я думаю, что это действительно хороший инструмент для программирования пользовательских интерфейсов.В принципе, для этого нужны простые структурированные программы, подобные этой:

void Foo(..args..){
  x = y;
  if (..some test..){
    Bar(arg1, ...)
  }
  while(..another test..){
    ...
  }
  ...
}

и гадости со структурой управления, подобной этой:

void deFoo(..args..){
  if (mode & 1){x = y;}
  {int svmode = mode; if (deIf(..some test..)){
    deBar(((mode & 1) arg1 : 0), ...)
  } mode = svmode;}
  {int svmode = mode; while(deIf(..another test..)){
    ...
  } mode = svmode;}
  ...
}

Итак, действительно хорошим способом сделать это было бы написать синтаксический анализатор для C или любого другого базового языка, а затем пройти по дереву синтаксического анализа, сгенерировав нужный мне код.(Когда я делал это на Lisp, эта часть была легкой.)

Но кто хочет написать синтаксический анализатор для C, C ++ или чего-то еще?

Итак, вместо этого я просто пишу макросы, чтобы иметь возможность писать код следующим образом:

void deFoo(..args..){
  PROTECT(x = y);
  IF(..some test..)
    deBar(PROTECT(arg1), ...)
  END
  WHILE(..another test..)
    ...
  END
  ...
}

Однако, когда я делаю это на C #, кто-то по своей мудрости решил, что макросы - это плохо, и я не хочу писать синтаксический анализатор C #, поэтому мне приходится генерировать код вручную.Это настоящая мука, но это все равно стоит того по сравнению с обычным способом кодирования подобных вещей.

Другие советы

Для c ++ я предпочитаю либо шаблонное метапрограммирование, либо генерацию кода вместо макросов, но макросы все еще имеют свое применение.

Пример, который вы привели с dbtemplatelib, может быть описан в c ++ 0x Вариативные Шаблоны, с дополнительными преимуществами, такими как проверка типа и т.д.

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

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

У обоих есть свои проблемы.В отличие от макросов, генерация кода может создавать читаемый и отлаживаемый (это вообще слово?) код, но он менее гибкий и его сложнее изменить.

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top