android之为什么 Yen (U+00A5) 符号的 Android Shift-JIS 编码会产生 -4,-4
运行以下代码似乎生成了错误的值:
byte[] data = "\u00a5".getBytes("Shift_JIS");
它产生 [ -4, -4 ],但我期望 [ 0x5c ]
我尝试了各种替代名称,“Shift-JIS”、“shift_jis”、“cp932”,并且都产生了相同的结果。
当我将结果数据输入 Shift-JIS 解码器时,出现异常:java.nio.charset.UnmappableCharacterException: Length: 2
即解码器配置如下:
Charset charset = Charset.forName("Shift_JIS);
CharsetDecoder decoder = charset.newDecoder()
.onMalformedInput(CodingErrorAction.REPORT)
.onUnmappableCharacter(CodingErrorAction.REPORT);
但考虑到编码器的输出看起来不对,我的猜测是解码器无关紧要。我的观点是,无论实际字节数如何,编码器都会生成它无法解码的数据。
全宽 Yen (U+FFE5) 编码为 [ -127 (0x81), -113 (0x8F) ],并正确解码。
奇怪的是,如果我尝试解码 [ 92 (0x5C) ] 这是我认为单宽度日元的 Shift-JIS 编码,Android/Java 解码器会生成一个反斜杠,将字符保留为 92。
如果编码器不支持给定的字符,我希望有一个替换字符,例如“?”。但是 -4 (0xFC) 似乎甚至不是有效的 Shift-JIS。它甚至不是 Unicode 替换字符 U+FFFD。 使用以下行我可以看到编码器似乎配置为使用 [-4, -4]:
Charset.forName("Shift_JIS").newEncoder().replacement()
- 那么为什么没有在 Shift-JIS 中映射单一宽度的日元?
- [-4, -4] 是一个合理的编码器替代品吗?
- 为什么解码器不支持 0x5C 映射到 Yen (U+00A5)?
- 如果 0x5C 不是正确的编码,那是什么?
请您参考如下方法:
部分答案:当微软为 Windows 创建其东亚代码页时,如日语代码页 932 和韩语代码页 949,他们将字节 0x5C
呈现为货币符号(要么是日元符号或韩元符号),同时在语法上仍充当文件路径中的反斜杠字符(因此日文系统上的文件路径可能看起来像
C:¥Documents¥something.doc
)。因此这个字节在某种意义上是一个日元符号,但在某种意义上也是一个反斜杠;根据 http://archives.miloush.net/michkap/archive/2005/09/17/469941.html,在日文系统中,根据字体,相同的字节甚至被呈现为这些符号中的不同符号。 .
编码中符号的含义缺乏一致意味着虽然 Shift-JIS 编码器 可以明智地映射 \
和 ¥
到字节 0x5C
,试图将 Shift-JIS 编码的字符串映射到一系列 unicode 代码点的解码器 无法知道是否转换字节 0x5C
到反斜杠或日元符号;日本用户过去常常通过他们的字体选择来做出选择(如果他们能够做出的话)。
面对这种无法修复的歧义,所有解码器似乎都选择将0x5C
解码为反斜杠。 (至少,Python 会这样做,并且 the WhatWG have a spec that dictates it 。)
关于在 shift_jis
中对日元符号进行编码时,Java/Android 正在做什么的细节,恐怕我不知道。
1.本站遵循行业规范,任何转载的稿件都会明确标注作者和来源;2.本站的原创文章,请转载时务必注明文章作者和来源,不尊重原创的行为我们将追究责任;3.作者投稿可能会经我们编辑修改或补充。