Какая точка #define
находится в С++? Я видел только примеры, где он использовался вместо "магического числа", но я не вижу смысла просто указывать это значение вместо переменной.
Зачем использовать #define вместо переменной
Ответ 1
В основном стилистика в наши дни. Когда C был молод, не было такой вещи, как переменная const. Поэтому, если вы использовали переменную вместо #define
, у вас не было гарантии, что кто-то где-то не изменит ее значение, вызывая хаос во всей вашей программе.
В старые времена FORTRAN передавал даже константы подпрограмм по ссылке, и было возможно (и побуждение головной боли) изменить значение константы типа "2" как нечто иное. Однажды это произошло в программе, над которой я работал, и единственный намек, который у нас был на то, что что-то не так: мы получили ABEND (ненормальный конец), когда программа попала в STOP 999
, который должен был закончить его нормально.
Ответ 2
#define
является частью языка препроцессора для C и С++. Когда они используются в коде, компилятор просто заменяет оператор #define
тем, что вы хотите. Например, если вам не нравится писать for (int i=0; i<=10; i++)
все время, вы можете сделать следующее:
#define fori10 for (int i=0; i<=10; i++)
// some code...
fori10 {
// do stuff to i
}
Если вам требуется нечто более общее, вы можете создать макросы препроцессора:
#define fori(x) for (int i=0; i<=x; i++)
// the x will be replaced by what ever is put into the parenthesis, such as
// 20 here
fori(20) {
// do more stuff to i
}
Это также очень полезно для условной компиляции (другое основное использование для #define
), если вы хотите, чтобы определенный код использовался в некоторой конкретной сборке:
// compile the following if debugging is turned on and defined
#ifdef DEBUG
// some code
#endif
Большинство компиляторов позволят вам определить макрос из командной строки (например, g++ -DDEBUG something.cpp
), но вы также можете просто ввести определение в свой код следующим образом:
#define DEBUG
Некоторые ресурсы:
- Статья в Википедии
- С++ специфический сайт
- Документация по препроцессору GCC
- Ссылка Microsoft
- C-специфический сайт (я не думаю, что это отличается от версии С++)
Ответ 3
У меня были проблемы с работой один раз. Меня обвинили в использовании "магических чисел" в объявлениях массива.
Вот так:
int Marylyn[256], Ann[1024];
Политика компании заключалась в том, чтобы избежать этих магических чисел, потому что мне объяснили, что эти цифры не переносимы; что они затрудняют простоту обслуживания. Я утверждал, что когда я читаю код, я хочу точно знать, насколько велик массив. Я проиграл аргумент, и поэтому в пятницу днем я заменил оскорбительные "магические числа" на #defines, например:
#define TWO_FIFTY_SIX 256
#define TEN_TWENTY_FOUR 1024
int Marylyn[TWO_FIFTY_SIX], Ann[TEN_TWENTY_FOUR];
В следующий понедельник днем меня вызвали и обвинили в пассивных вызывающих тенденциях.
Ответ 4
C не использовал константы, поэтому #defines были единственным способом предоставления постоянных значений. И C и С++ имеют их сейчас, поэтому нет смысла их использовать, кроме случаев, когда они будут протестированы с помощью # ifdef/ifndef.
Ответ 5
#define
может выполнять некоторые задания, которые обычный С++ не может, например, защищать заголовки и другие задачи. Тем не менее, это определенно не должно использоваться как магическое число - вместо этого следует использовать статический const.
Ответ 6
Наиболее распространенное использование (кроме объявления констант) - это включить охрану.
Ответ 7
Определить оценивается перед компиляцией препроцессором, а переменные - во время выполнения. Это означает, что вы контролируете, как создается ваше приложение (а не как оно работает)
Вот несколько примеров, которые используют define, который не может быть заменен переменной:
-
#define min (i, j) (((i) < (j))? (i): (j))
обратите внимание, что это оценивается препроцессором, а не во время выполнения
Ответ 8
#define
позволяет установить значение в заголовке, который в противном случае компилировался бы с размером больше или больше нуля. Ваши заголовки не должны компилироваться с размером больше-больше нуля.
// File: MyFile.h
// This header will compile to size-zero.
#define TAX_RATE 0.625
// NO: static const double TAX_RATE = 0.625;
// NO: extern const double TAX_RATE; // WHAT IS THE VALUE?
EDIT: Как указывает Нил в комментарии к этому сообщению, явное определение-со значением в заголовке будет работать для С++, но не C.