c - 为什么 `strchr` 似乎适用于多字节字符,尽管有手册页免责声明?

标签 c string utf-8 wchar-t

来自:

man strchr

char *strchr(const char *s, int c);

The strchr() function returns a pointer to the first occurrence of the character c in the string s.

Here "character" means "byte"; these functions do not work with wide or multibyte characters.

不过,如果我尝试搜索多字节字符,例如 é(UTF-8 中的 0xC3A9):

const char str[] = "This string contains é which is a multi-byte character";
char * pos = strchr(str, (int)'é');
printf("%s\n", pos);
printf("0x%X 0x%X\n", pos[-1], pos[0]); 

我得到以下输出:

� which is a multi-byte character

0xFFFFFFC3 0xFFFFFFA9

尽管警告:

warning: multi-character character constant [-Wmultichar]

所以这是我的问题:

  • strchr 不适用于多字节字符是什么意思? (它似乎 工作,前提是 int 类型足够大以包含最多 4 个字节的多字节)
  • 如何摆脱警告,即如何安全地恢复多字节值并将其存储在 int 中?
  • 为什么前缀 0xFFFFFF

最佳答案

strchr() 似乎只适用于您的多字节字符。

内存中的实际字符串是

... c, o, n, t, a, i, n, s, ' ', 0xC3, 0xA9, ' ', w ...

当您调用 strchr() 时,您实际上只是在搜索 0xA9,即低 8 位。这就是为什么 pos[-1] 具有多字节字符的第一个字节:它在搜索过程中被忽略了。

char 在您的系统上是有符号的,这就是为什么您的字符在打印时会进行符号扩展(0xFFFFFF)。

至于警告,似乎编译器试图告诉您您正在做一些奇怪的事情,而您确实是这样。不要忽视它。

关于c - 为什么 `strchr` 似乎适用于多字节字符,尽管有手册页免责声明?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/25566356/

相关文章:

php - 从数据库 php 中以 utf-8 格式读取单词

mysql - 如何在 phpMyAdmin 中显示 UTF-8 字符?

c - 在哪里可以找到适合新手学习 C 编程的简单视频类(class)

c - 是否可以动态选择 UNION 下的 2 个结构之一?

python - 在 Python 中将 sql 查询存储为单个变量

c++ - 如何将 char 数组文本存储在字符串中?

json - 尝试仅从Windows将大容量数据加载到ElasticSearch中的JSON编码问题

c - "make clean"导致 "make all"失败

java - 在 Java 中有效存储包含原语的对象数组

javascript - 如何解析 key :value pair on JSON-like string with RegEx on JavaScript?