开发者

C++ Macro is not replacing all values

开发者 https://www.devze.com 2022-12-28 00:47 出处:网络
I have the following 2 macros: #define SCOPED_ENUM_HEADER(NAME) struct NAME{ enum _NAME{ #define SCOPED_ENUM_FOOTER(NAME) };}; typedef NAME::_NAME NAMEtype;

I have the following 2 macros:

#define SCOPED_ENUM_HEADER(NAME) struct NAME{ enum _NAME{
#define SCOPED_ENUM_FOOTER(NAME) };}; typedef NAME::_NAME NAMEtype;

Only the first instance of NAME get replaced by the passed NAME. What's wrong with it?

Is is to be used in such a way:

 SCOPED_ENUM_HEADER(LOGLEVEL)
   UNSET,
   FILE,
   SCREEN
 SCOPED_ENUM_F开发者_运维技巧OOTER(LOGLEVEL)


The problem is that NAME is not the same as _NAME; they are two totally separate identifiers.

If you want to add an underscore to the front of whatever the parameter NAME is, use the concatenation (##) operator:

_##NAME

You do need to be really careful with prepending an underscore, though. All identifiers beginning with an underscore followed by a capital letter are reserved to the implementation.


You only have one instance of NAME in each macro. You also have an example of _NAME in each macro, but that's highly questionable: names beginning with an underscore and having a capital letter following are reserved for the implementation, and so you could have a problem there.

However, you want to take the value of NAME and concatenate something to it, let's say putting a E_ in front. This is a little tricky, since _##NAME will normally get you _NAME, no matter what you put in.

This is explained on the C++ FAQ Lite, but what you really have to do is something like:

#define REALLY_CONCATENATE(a,b) a ## b
#define CONCATENATE(a,b) REALLY_CONCATENATE(a,b)
#define SCOPED_ENUM_HEADER(NAME) struct NAME{ enum CONCATENATE("E_", NAME) {

(sorry, can't test this right now).

On the other hand, there has got to be a better way to do what you're doing. Seriously.

0

精彩评论

暂无评论...
验证码 换一张
取 消

关注公众号