Scanf () with C ++ Enumerations

The following is a typical situation in our code base.

enum ConfigOption { CONFIG_1=1, CONFIG_2=2, CONFIG_3=3 }

ConfigOption cfg1, cfg2;

sscanf(s, "%d", &cfg1);

This is an internally used simulation software. Does not apply. Ease of maintenance and correctness are essential. Portability and user interface - not really.

The problem enumin C ++ is not necessary int. Thus, we get a warning about the compiler and may get the wrong behavior when using another compiler or when optimization is turned on.

One solution is to simply drop it &cfgbefore int*. However, this will not catch cases when the compiler decided to allocate intsomething other than int.

So, I suggested the following solution:

template<typename T> inline
int& eint(T& enum_var) {
    assert(sizeof(T) == sizeof(int));
    return (int&)enum_var;
}

And now we use scanfas follows:

sscanf(s, "%d", &eint(cfg1));

() . , - . " ", , .

+3
4

, vs2010,

enum class ConfigOption: unsigned int {CONFIG_1=1, CONFIG_2=2, CONFIG_3=3};

++ 0x

+4

, enum . , Microsoft DirectX ( , ).

int, , :

typedef enum 
{
  fooo = 1,
  baar = 2,
  ___Force32Bit = ~0UL
} MyEnum;

int.

, , , :

typedef enum 
{
  fooo = 1,
  baar = 2,
  ___Force64Bit = ~0ULL
} MyEnum;

, . , , . , , 32 64- , , .

Btw - C-, , ++, C-: -)

+2

int?

enum ConfigOption { CONFIG_1=1, CONFIG_2=2, CONFIG_3=3 };
ConfigOption cfg1;

int i;
sscanf(s, "%d", &i);
cfg1 = i;

(, , enum).

(, , strtol strtoul sscanf.)

+1
source

You can try to use boost::lexical_cast, or if you are not using boostand do not want to use it for this case, you can simply write a simplified version of this. See this SO answer for an example .

0
source

Source: https://habr.com/ru/post/1758586/


All Articles