2009-10-03 94 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