Как вы обнаружили, вы не можете сделать это в как вы пытались. Макро-расширение просто не имеет встроенной условной оценки, поэтому вам придется создавать несколько макросов.
Однако, если вы просто пытаетесь «оптимизировать» нормальный поток кода, вы можете положиться на оптимизацию вашего компилятора. Рассмотрим это:
if (true) {
std::cout << "Hi\n";
}
В результате программа не будет иметь каких-либо условных проверок в нем, потому что true
всегда truthy.
Аналогично:
if (false) {
std::cout << "Hi\n";
}
В результате программа не будет содержать код для получения вывода, потому что false
никогда не truthy.
Аналогично:
if (4 != 4) {
std::cout << "Hi\n";
}
Программа будет по-прежнему не содержит std::cout
код.
Во многих случаях, вы можете использовать этот факт, чтобы сохранить код простым и достичь желаемого эффекта:
#define BAR(X) \
if ((X) == 4) {
std::cout << "hi" << std::endl;\
}
Ограничения здесь, конечно, является то, что if
заявление должно быть действительным в том месте, напишите BAR(5)
, или BAR(42)
или BAR(999)
.
Это также гибко, поскольку теперь вы можете использовать значение времени выполнения (например, BAR(i)
), и хотя условное выражение больше не может быть свернуто во время компиляции, в таком случае у вас нет причин ожидать, что так или иначе ,
Я использую этот подход в своем макрокоманде регистрации: макрос при вызове для LOG_LEVEL_DEBUG
расширяет условное обозначение, которое статически известно никогда, чтобы не совпадать, в версиях сборки.
Идея позволяет компилятору оптимизировать.
Вы также захотите рассмотреть возможность использования a little macro expansion trick to avoid problems with subsequent else
clauses.
Но зачем вам нужно это сделать с препроцессора? – SingerOfTheFall
Нормальное, если условие может работать также ...? – NaCl
Я использую X-macro https://en.wikipedia.org/wiki/X_Macro, и мне нужна условная компиляция при ее расширении – Gulzar