C中的无符号字符未按预期工作
Posted
技术标签:
【中文标题】C中的无符号字符未按预期工作【英文标题】:unsigned char in C not working as expected 【发布时间】:2021-08-17 19:05:20 【问题描述】:由于 unsigned char 表示 0 - 255,而 'à' 的扩展 ascii 代码是 133,我希望下面的 C 代码打印 133
unsigned char uc;
uc='à';
printf("%hhu \n",uc);
相反,clang 和 gcc 都会产生以下错误
error: character too large for enclosing character literal type
uc='à';
^
出了什么问题?
顺便说一句,我从法语网站复制了 à 并将结果粘贴到赋值语句中。我怀疑我创建 à 的方式可能无效。
【问题讨论】:
您的编辑器使用的是 UTF-8 编码,而不是扩展的 ASCII。 您的编译器很可能将您的源代码视为 UTF-8 而不是 ASCII。而在 UTF-8 中,字母“à”表示为两个字节序列 0xC3 0xA0,因此不适合char
,无论是有符号还是无符号。
字符 à 不能在 C 程序中使用。尝试使用 \x85。
@YvesDaoust 你有规范参考的链接吗?
没有“扩展 ascii”这样的东西。有些人在一两年前用这个词来表示几个不相容的东西。今天没有理由使用它。
【参考方案1】:
因为 unsigned char 代表 0 - 255
在大多数实现中都是如此,但 C 标准不要求 char
限制为 8 位,它可以更大并支持更大的范围。
'à'的扩展ASCII码是133,
可能有一个 C 实现,其中 'à'
的值为 133 (0x85),但由于大多数实现使用 Unicode,'à'
可能使用最有可能存储为 UTF-8 的代码点 224 (0xE0)。您的编辑器也设置为 UTF-8,因此需要多个字节来表示 ASCII 以外的字符。在 UTF-8 中,所有 ASCII 字符都像 ASCII 一样存储,需要 1 个字节,所有其他字符都是 2-4 个字节的组合,并且每个字符都设置了第 7 位。我建议您了解 UTF-8 的工作原理,UTF-8 是大多数情况下存储文本的最佳方式,因此您应该仅在有充分理由时才使用其他方式。
我希望下面的 C 代码打印 133
在 UTF-8 中,à 的代码点存储为 0xC3 0xA0,组合成值 0xE0。您不能将 0xC3 0xA0 存储在 8 位 char
中。所以clang报错。
您可以尝试将其存储在int
、unsigned
、wchar_t
或其他一些足够大的整数类型中。 GCC 将存储值 0xC3A0 而不是 0xE0,因为这是 ''
中的值。但是,C 支持宽字符。 wchar_t
可能支持更多字符的类型很可能wchar_t
在您的系统上是 32 或 16。要编写宽字符文字,您可以使用前缀 L
。使用宽字符文字,编译器将存储正确的值 0xE0。
将代码改为:
#include <wchar.h>
....
wchar_t wc;
wc=L'à';
printf("%u \n",(unsigned)wc);
【讨论】:
此答案的编写方式不会向不熟悉字符集并通过字节表示的人解释。 “第 7 位被设置在每一个中”与“à 的代码点存储为 0x3C 0xA0”相矛盾,因为第 7 位未在 0x3C 中设置。 @EricPostpischil 谢谢,已修复。以上是关于C中的无符号字符未按预期工作的主要内容,如果未能解决你的问题,请参考以下文章