【问题标题】:Is it possible there will be an encoding error when reading a character?读取字符时是否可能会出现编码错误?
【发布时间】:2016-01-09 08:08:36
【问题描述】:

如果在解释宽字符时发生编码错误,该函数将 errno 设置为 EILSEQ。

scanf("%d", &i);

如果输入大于2147483648(如果isigned int),scanf会改变errno的值。

但是如果我尝试读取一个字符,像这样:

scanf("%c", &c);

是否可以输入导致编码错误的字符?我已经使用 UTF-8 输入对其进行了测试,但效果很好(c 的十进制代码是 -32,但 errno0)。

【问题讨论】:

  • %c 不支持宽字符。 %lc 将是相关的转换说明符。
  • 您的程序完全按预期运行。您的泰米尔语 Unicode 字符 的第一个字符值 U+0BEE 在 UTF8 表示法中确实是 224。当解释为 signed 字符值时,即是您得到的 -32

标签: c input error-handling scanf errno


【解决方案1】:

首先,您需要为宽字符使用不同的转换说明符:

wchar_t c;
scanf("%lc", &c);

您的问题的答案是“是”,您应该始终检查输入是否有效!

用户键入一个无效字符实际上是不可能的(键盘只能产生有效字符),但输入可以来自其他来源,并且在大多数情况下您无法预测那些提前。输入字符集也可能与您的程序认为的不匹配(在这种情况下,您会遇到更大的问题,但检查无效编码将有助于更快地发现问题)。

无论如何,检查scanf 的返回值的方法与检查malloc 的返回值的方法相同(你这样做 这样做,对吗?)

if (scanf("%lc", &c) != 1)
  emit_input_error_and_abort();

【讨论】:

  • 我总是检查scanf 的返回值,因为我知道在我的程序中输入是纯ASCII 的,现在就足够了。但是,你知道check_encoding(); scanf("a character", &c); 会改变errno 的值的例子吗?
  • 我不知道“check_encoding”是做什么的? scanf 将永远无法读取 %c 非宽字符,除非您点击 EOF、ENOMEM 或其他非实际输入的返回码之一。
  • 如果cchar,该函数将检查输入的编码。如果是 UTF-8,函数会显示错误消息。或类似的东西。 :D 我只想知道errno 何时更改。 #1:变量是数字类型,输入超出范围。 #2:???我想如果我输入也会导致 OoR 的 UTF-8 字符,就像数字一样,scanf 会更改 errno,但不是。我必须检查errno的任何其他示例?
  • 当 scanf 返回预期之外的任何数字时,您必须始终检查 errno。 errno 的值在其他任何时候都应该被认为是未定义的,如果你有两次相同的错误,检查它的变化是不够的。
猜你喜欢
  • 2018-03-11
  • 2013-03-27
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-07-11
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多