1

我已将 Xcode iOS 项目从 Xcode 3.2.6 迁移到 4.2。现在,当我尝试使用带有非 ASCII 字符的文字初始化 wchar_t 时,我收到了警告:

wchar_t c1;
if(c1 <= L'я') //That's Cyrillic "ya"

消息是:

MyFile.cpp:148:28:警告:字符 unicode 转义序列对其类型而言太长 [2] MyFile.cpp:148:28:警告:忽略宽字符常量中的无关字符 [2]

并且文字没有按预期工作 - 比较失败。

我正在使用 -fshort-wchar 进行编译,源文件是 UTF-8 格式。Xcode 编辑器可以正常显示文件。它在 GCC(包括 Xcode 3 在内的多种版本)上编译和工作,在 MSVC 上工作。有没有办法让 LLVM 编译器识别这些文字?如果没有,我可以回到 Xcode 4 中的 GCC 吗?

编辑:Snow Leopard 上的 Xcode 4.2 - 长篇大论。

EDIT2:确认了一个全新的项目。文件扩展名无关紧要 - .m 文件中的行为相同。-fshort-wchar 也不影响它。看起来我必须回到 GCC,直到我可以升级到修复此问题的 Xcode 版本。

4

3 回答 3

2

不是答案,但希望是有用的信息——我无法用 clang 4.0 (Xcode 4.5.1) 重现问题:

$ uname -a
Darwin air 12.2.0 Darwin Kernel Version 12.2.0: Sat Aug 25 00:48:52 PDT 2012; root:xnu-2050.18.24~1/RELEASE_X86_64 x86_64
$ env | grep LANG
LANG=en_US.UTF-8
$ clang -v
Apple clang version 4.0 (tags/Apple/clang-421.0.60) (based on LLVM 3.1svn)
Target: x86_64-apple-darwin12.2.0
Thread model: posix
$ cat test.c
#include <stdio.h>
#include <stdlib.h>

int main(void)
{
    wchar_t c1 = 0;
    printf("sizeof(c1) == %lu\n", sizeof(c1));
    printf("sizeof(L'Я') == %lu\n", sizeof(L'Я'));
    if (c1 < L'Я') {
        printf("Я люблю часы Заря!\n");
    } else {
        printf("Что за....?\n");
    }
    return EXIT_SUCCESS;
}

$ clang -Wall -pedantic ./test.c 
$ ./a.out 
sizeof(c1) == 4
sizeof(L'Я') == 4
Я люблю часы Заря!
$ clang -Wall -pedantic ./test.c -fshort-wchar
$ ./a.out 
sizeof(c1) == 2
sizeof(L'Я') == 2
Я люблю часы Заря!
$ 

使用 clang++(其中wchar_t是内置类型)观察到相同的行为。

于 2012-10-26T03:44:57.077 回答
1

对于您的具体问题,我没有答案,但想指出 llvm-gcc 已永久停产。根据我处理 Clang 和 llvm-gcc 以及 gcc 之间的 delta 的经验,Clang 在 C++ 规范方面通常是正确的,即使这种行为令人惊讶。

于 2012-10-26T03:36:57.653 回答
1

如果实际上源是 UTF-8,那么这不是正确的行为。但是我无法在最新版本的 Xcode 中重现该行为

MyFile.cpp:148:28:警告:字符 unicode 转义序列对其类型而言太长 [2]

这个错误应该是指一个“通用字符名称”(UCN),它看起来像“\U001012AB”或“\u0403”。它表示转义序列表示的值大于封闭的文字类型能够容纳的值。例如,如果代码点值需要超过 16 位,则 16 位 wchar_t 将无法保存该值。

MyFile.cpp:148:28:警告:宽字符常量中的无关字符被忽略 [2]

这表明编译器认为在宽字符文字中表示的代码点不止一个。例如L'ab'。行为是实现定义的,clang 和 gcc 都只使用最后一个代码点值。

您显示的代码不应该触发其中任何一个,至少在clang中。第一个是因为这只适用于 UCN,更不用说 'я' 很容易适合单个 16 位 wchar_t 的事实;第二个是因为他的源代码编码总是被认为是 UTF-8,它会将 'я' 的 UTF-8 多字节表示视为单个代码点。

您可以重新检查并确保源实际上是 UTF-8。然后你应该检查你使用的是最新版本的 Xcode。您也可以尝试在项目设置中切换编译器 > Compile for C/C++/Objective-C

于 2012-10-26T04:27:05.433 回答