0
#include <iostream>

#define MY_CONST 10

#define MY_OTHER_CONST MY_CONST

#undef MY_CONST

int main() {

  enum my_enum : int {

    MY_CONST = 100
  };

  std::cout << MY_OTHER_CONST;

  return 0;

}

I would expect 10 as an output, but this program outputs 100. Can someone explain what is going on here?

https://godbolt.org/z/77EedG11x

Marek R
  • 32,568
  • 6
  • 55
  • 140
user3600124
  • 829
  • 1
  • 7
  • 19
  • Macros are expanded lazily. The compiler doesn't look at the definition of `MY_OTHER_CONST` until you try to use it outside of a `#define`. – HolyBlackCat Jul 14 '22 at 13:08
  • `MY_OTHER_CONST` isn't expanded until you hit `std::cout << MY_OTHER_CONST` and at that point the `MY_CONST` is #undeffed. – Lundin Jul 14 '22 at 13:10
  • 3
    You can just run the preprocessor on your source file to see what the file looks at after preprocessing. `gcc -E foo.cpp` for gcc. – Eljay Jul 14 '22 at 13:13
  • undef practically always spells trouble. I recommend to supersticiously avoid it. If you think you need it for something, it is time to redesign. Even the widely used X-macros can be done without. – Yunnosch Jul 14 '22 at 13:16

1 Answers1

3

#define MY_OTHER_CONST MY_CONST defines the macro MY_OTHER_CONST to have a replacement list of MY_CONST. No replacement is performed when defining a macro.

In std::cout << MY_OTHER_CONST;, MY_OTHER_CONST is replaced by its replacement list, becoming MY_CONST. At this point, there is no macro definition for MY_CONST, so no further replacement is performed. Then MY_CONST refers to the enum constant MY_CONST, which has value 100.

Eric Postpischil
  • 195,579
  • 13
  • 168
  • 312
  • Is there a way to save the value of `MY_CONST` macro and then `#undef MY_CONST`? Because I need this specific name for other uses – user3600124 Jul 14 '22 at 13:15
  • If you have a name conflict solve it differently. There is a duplicate on that, if you don't mind an upvoted answer by me on it.... https://stackoverflow.com/questions/60174589/undef-seems-to-have-no-effect-on-macro-redefinitions-warning-c4005 There are some variations, also with duplicates. – Yunnosch Jul 14 '22 at 13:17
  • 1
    @user3600124 In C++ you only need macros in some rather specific situations. They can usually be replaced by C++ core language features. In particular for defining constants they are completely unnecessary. Declare your constants as `constexpr auto` variables in appropriate namespaces instead. – user17732522 Jul 14 '22 at 13:20
  • I am using some old-school C library, where those `#define`'s are used – user3600124 Jul 14 '22 at 13:22