2009-10-03 105 views
1

我需要将枚举成员(其值,而不是标识符)转换为字符串。 我已经尝试了以下,它适用于MACRO(TYPE_A),但不适用于枚举值(typeA)。这在我看来有点奇怪。枚举成员上的字符串化

你有什么想法如何做到这一点?

 

#define _tostr(a) #a 
#define tostr(a) _tostr(a) 

typedef enum _SPECIAL_FOLDER_ID { 
    typeA = 3, 
    typeB = 4, 
} SPECIAL_FOLDER_ID; 

#define TYPE_A 3 

int main() { 
    //this is working, but the information is a macro (TYPE_A) 
    printf("The string is " tostr(TYPE_A) ".\n"); 

    //this is not working for typeA (defined in an enumeration) 
    printf("The string is " tostr(typeA) ".\n"); 
    return 0; 
} 

 

输出是:

 
The string is 3. 
The string is typeA. 

我需要修改代码以某种方式使输出的第二行会“字符串3”。

谢谢!

PS:我不想用printf打印这个值。我需要一个包含该值的静态字符串。我只使用printf来测试结果...

+0

请详细说明您的奇怪要求。如果你需要字符串,你可以使用sprintf()而不是printf()。 – qrdl 2009-10-03 18:55:43

回答

5

预处理器不知道C.它只是知道“文本”。
当它处理您的文件时,typeA只是5个字母。只有编译器会知道(在预处理器完成后)typeA有一个值,并且该值为3.

+1

是挑剔的:预处理器知道什么是预处理令牌 – Christoph 2009-10-03 17:08:44

+0

http://99-bottles-of-beer.net/language-c-c++-preprocessor-115.html 可以使预处理器(kinda)智能化:) – pmg 2009-10-03 17:24:31

2

以下是什么错误?

printf("The string is %d.\n", typeA); 

你似乎有所过于复杂的问题......

+0

你打我18秒:) – qrdl 2009-10-03 15:31:07

+0

我不想打印字符串,但需要一个具有该表示的静态字符串。问题不在于printf这里... – botismarius 2009-10-03 16:22:04

+0

那么,AFAIK,你不能这样做。 您可以创建一个与枚举长度相同的字符串数组,并手动更新它。但是我不知道其他方式。 – Goz 2009-10-03 16:54:51

0

出了什么问题好老格式化输出?

printf("The string is %d", typeA) 
+0

我需要一个包含该值的静态字符串(编译时已知的字符串) – botismarius 2009-10-03 16:23:14

+0

-1因为@botismarius很清楚,它不是他们想要的。为什么这对他们不起作用并不能回答这个问题。 – Aftermathew 2009-10-03 18:54:14

+0

@Aftermathews我已经回答了原来的问题,OP之后编辑了这个问题,所以你的downvote是不公平的。 – qrdl 2009-10-03 19:00:58

1

使用两个嵌套宏是强制预处理器展开任何宏参数(TYPE_A - > 3)的技巧。

但是,枚举值并未被预处理器扩展,它们由编译器扩展。

0

由于编译器将ENUM转换为文字数字,因此没有自动方法可以执行此操作。

简单的方法是有一个静态的字符串数组,并小心保持同步。

炭名称[] [8] { “”, “”, “”, “的typeA”, “类型B”,等}
然后,只需使用 “名称[的typeA]”

一个更安全的方法是有一个大开关语句的函数。

3

有没有一个很好的方法来实现这一点。最好的我可以拿出是

#define typeA_ 3 
#define typeB_ 4 

enum 
{ 
    typeA = typeA_, 
    typeB = typeB_ 
}; 

#define tostr__(E) #E 
#define tostr_(E) tostr__(E) 
#define tostr(E) tostr_(E ## _) 
1

我倾向于使用静态数组的方法。这仍然是一个难题,但它相当清楚,它的工作原理。

enum { 
    typeA = 3, 
    typeB = 4, 
    NUM_LETTERS = 5 
} Letters; 

static const char* letterNames[NUM_LETTERS] { 
    "", "", "", 
    "3", 
    "4" 
}; 

printf("The string is " letterNames[(int)typeA] ".\n"); 

看起来好像克里斯托弗的回答是不错的,但我必须说实话,我不是非常熟悉,宏去理解它;-)

编辑;另一种方法:你提到你想要一个'静态字符串',但我不确定你在编译时需要它。你可以在运行开始时使用sprintf吗?该解决方案将是这个样子......

enum { 
    typeA = 3, 
    typeB = 4, 
    NUM_LETTERS = 5 
} Letters; 


int main(void){ 
    char * typeAString = new char[sizeof("This is at least as long as the typeA string")]; 
    sprintf(typeAString, "This is the %d string", typeA); 
    // use your string here 
    return 0; 
} 

我用新这里是不是我会建议的方式,但它显示在你的程序中使用的sprintf的想法。

+0

我不能让你的代码片段编译。 – pmg 2009-10-03 19:20:14