2017-02-28 42 views
1

我有得到我的構建腳本生成,並通過資源文件包含(#include).h文件,但由於(TM)符號的它不會建:Can one#定義包含資源文件的非ANSI字符的文字字符串嗎?

#define PRODUCT_NAME Acme Widget™ 1.2.3 

我得到的回覆是錯誤CommonAssemblyInfo.h(7): error RC2018: unknown character '0xe2'

很明顯,我可以通過使用TM來解決它,但我更願意使用「正確」符號。可以這樣做嗎?


UPDATE

我本來應該在描述問題和我道歉,更完整。事實證明,我忽略了一個重要的細節:所涉及的頭文件正在被資源文件包含,因此錯誤來自資源編譯器。我正在更新這篇文章的標題以反映事實。

+0

嘗試一對引號。 – bmargulies

+3

一開始:爲什麼不在文本週圍添加'''?它應該是一個字符串文字,然後你應該檢查你的編碼。具體問題:提供一個[mcve]你爲什麼要添加UTF-8標籤?你確定這是UTF-8?編譯器使用哪個輸入字符集?哪個輸出字符集? – Olaf

+0

原則上,你應該能夠使用\ u2122來表示™(U + 2122或UTF-8中的十六進制字節E2 84 A2) –

回答

0

事實證明,在Visual C++資源編譯器不理解UTF-8,但只知道ANSI和Unicode:

https://connect.microsoft.com/VisualStudio/feedback/details/214917/

RC編譯器支持UTF-16。至於UTF-8,它目前不受RC編譯器的支持。這種不方便的解決方法是使用Visual Studio另存爲功能將rc文件轉換爲UTF-16。

該錯誤在2006年10月24日 - 十多年前被封爲「按設計」。可惜UTF-8還沒有趕上.../s

果然,當我將該文件保存爲Unicode時,一切都很順利。

1

C11具有UTF-8編碼的字符串文字的語法。爲了您的特定字符串,它看起來像這樣(假設源,或者至少這其中的一部分,在UTF-8編碼):

#define PRODUCT_NAME u8"Acme Widget™ 1.2.3" 

C不提供其基本字符集以外的字符出現在寬/ Unicode字符串文字之外的源文件中,儘管一些實現可能將它們作爲擴展名接受。

另一種方法是對編碼的字節嵌入到一個普通的字符串字面量,或甚至原宏替換文本:

#define PRODUCT_NAME Acme Widget\xE2\x84\xA2 1.2.3 

然而這沒多大用的省略字符串分隔符,因爲十六進制轉義語法僅在字符串和整數字符文字的上下文中有意義。

然而,大多數便攜式應用將使用Unicode轉義,正如@chux在註釋中所示。在這種情況下,不過,我看不出有什麼缺點給整個字符串爲UTF-8字符串字面量:

#define PRODUCT_NAME u8"Acme Widget\u2122 1.2.3" 
+1

也許''Acme Widget「u8」\ u2122「」1.2.3「'避免使用'™' – chux

+0

好建議@chux,儘管在這種情況下我沒有看到任何優勢來分隔UTF-8部分並依靠st環串聯。 –

+1

同意這種情況。如果OP想要''... Widget™1 ...「'(無空格),則需要分離,因爲」Widget \ u2112「不正確。通過隔離,作爲一般風格,避免了這個錯誤。 – chux

1

在Mac(運行MacOS的塞拉利昂10.12.3與GCC 6.3.0),在終端與區域由LANG=en_US.UTF-8設置,以下變化都編譯:

#include <stdio.h> 

#define PRODUCT_STRING  "Acme Widget™ 1.2.3" 
#define PRODUCT_UTF8  "Acme Widget\u2122 1.2.3" 

#define PRODUCT_NAME  Acme Widget™ 1.2.3 
#define STRINGIFY(x)  # x 
#define CVT_TO_STRING(x) STRINGIFY(x) 

int main(void) 
{ 
    puts(CVT_TO_STRING(PRODUCT_NAME)); 
    puts(PRODUCT_STRING); 
    puts(PRODUCT_UTF8); 
    return 0; 
} 

編譯:

$ gcc -O3 -g -std=c11 -Wall -Wextra -Werror -Wmissing-prototypes \ 
>  -Wstrict-prototypes -Wold-style-definition tm17.c -o tm17 
$ 

的輸出,你會不會驚訝地得知,是:

Acme Widget™ 1.2.3 
Acme Widget™ 1.2.3 
Acme Widget™ 1.2.3 

理論上,\u2122是最好的(最便攜的)符號使用。

我也測試過#define PRODUCT_NAME Acme Widget\u2122 1.2.3;編譯並生成相同的輸出。

Unicode escapes被添加到C99;您可能需要指定-std=c99-std=gnu99(或使用C11代替)以獲取所需結果。

0

嘗試:

更換™對Unicode \ u2122

使用引號

#define PRODUCT_NAME "Acme Widget\u2122 1.2.3"