"#define" против "#define 1" - PullRequest
       14

"#define" против "#define 1"

4 голосов
/ 17 марта 2020

В следующем примере 1 кажется ненужным (и, возможно, вводящим в заблуждение), но я видел это несколько раз, когда его использовали для проверки #ifdef s:

#ifndef __NEWLIB_H__

#define __NEWLIB_H__ 1

Есть ли разница или причина? за использование вышеприведенного и простого #define __NEWLIB_H__?

Ответы [ 3 ]

4 голосов
/ 17 марта 2020

1 - истина, поэтому вы можете использовать макрос в тесте #if. Это обычно не очень полезно для охранников заголовка, но это, конечно, не повредит. Для других макросов, которые могут быть протестированы в логических выражениях, истинное значение определенно полезно.

Некоторым людям просто нравится согласованность. И это определение, которое gcc выбирает по умолчанию, если вы ставите -D TESTME в командной строке.

Однако

#define __NEWLIB_H__ 1

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

3 голосов
/ 17 марта 2020

При использовании исключительно в качестве #include охранника нет никакой разницы между

#ifndef __NEWLIB_H__
#define __NEWLIB_H__

и

#ifndef __NEWLIB_H__
#define __NEWLIB_H__ 1

Однако, как правило, существует различие.

Ошибка компилятора

#ifndef ABCD
#define ABCD
#endif

int main()
{
#if defined(ABCD) && (ABCD == 1)
   std::cout << "ABCD is 1\n";
#else
   std::cout << "ABCD is not 1\n";
#endif
}

Вывод строки "ABCD is 1"

#ifndef ABCD
#define ABCD 1
#endif

int main()
{
#if defined(ABCD) && (ABCD == 1)
   std::cout << "ABCD is 1\n";
#else
   std::cout << "ABCD is not 1\n";
#endif
}

Вывод строки "ABCD is not 1"

#ifndef ABCD
#define ABCD 10
#endif

int main()
{
#if defined(ABCD) && (ABCD == 1)
   std::cout << "ABCD is 1\n";
#else
   std::cout << "ABCD is not 1\n";
#endif
}
1 голос
/ 17 марта 2020

#define само по себе заменит символ ничем .

С другой стороны, #define 1, как вы его называете, заменит символ везде 1 везде это найдено в файле. Так, например, следующий код:

#include <iostream>

#define EXAMPLE "hello"

int main()
{
    std::cout << EXAMPLE;

    return 0;
}

print

hello

Это потому, что здесь EXAMPLE заменен на "hello", что делает оператор print эквивалентным:

std::cout << "hello";

Если вместо этого вместо #define изменить выражение:

#define EXAMPLE

Это даст ошибку компиляции :

main.cpp: In function ‘int main()’:
main.cpp:15:25: error: expected primary-expression before ‘;’ token
     std::cout << EXAMPLE;

Что касается того, почему вы когда-либо используете эту вторую форму #define, это потому, что есть другая директива процессора, которую вы можете использовать, которая называется #ifdef:

#include <iostream>

#define EXAMPLE

int main()
{
#ifdef EXAMPLE
    std::cout << "EXAMPLE defined.";
#endif

    return 0;
}

Это напечатает :

EXAMPLE defined.

Поскольку #ifdef (и его относительный #ifndef) требуют только определения символа, нам не нужно давать ему значение. Просто нужно быть там, чтобы работать.

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

...