了解 Unicode:代理块、非字符

Hen*_*ing 4 unicode encoding utf-8 utf-16

我试图真正了解 unicode 标准,并且正在浏览xml 规范,其中写道:

字符 ::= #x9 | #xA | #xD | [#x20-#xD7FF] | [#xE000-#xFFFD] | [#x10000-#x10FFFF] /* 任何 Unicode 字符,不包括代理块、FFFE 和 FFFF。*/

现在我有几个问题:

  • 什么是代理块?它们是表示 4 字节代码点的 UTF-16 代码吗?
  • #xXXXX 是指代码点还是此处的 UTF-16 编码值?
  • 如果它指的是代码点并且我对代理块的理解是正确的:为什么这里提到代理块?从编码映射的空间中隐藏那些与编码相关的细节不是编码的任务吗?
  • 为什么像“U+FFFE”这样的非字符被定义为 unicode 标准的一部分?据我所知,字节顺序检测(以及处理灵活大小的代码字)取决于编码。

谢谢澄清!

Rem*_*eau 6

什么是代理块?

U+D800toU+DFFF范围内的Unicode 代码点(含),保留专供 UTF-16 代理使用,在任何其他上下文中都是非法的。

它们是表示 4 字节代码点的 UTF-16 代码吗?

是的。

#xXXXX 是指代码点还是此处的 UTF-16 编码值?

实际的 Unicode 代码点。考虑到Char包含值的定义> #xFFFF,单个编码的 UTF-16 值不能超过。UTF 是代码点值的字节编码方案。XML 规范是根据代码点而不是编码编写的。出于存储和传输的目的,可以使用 XML prolog 的“encoding”属性中指定的任何字符集对 XML 文档进行编码,但实际的 XML 内容是根据未编码的代码点处理的。

如果它指的是代码点并且我对代理块的理解是正确的:为什么这里提到代理块?

代理代码点是保留的,不允许在任何文本内容中出现未编码。该Char定义只是强制执行该规则。

为什么像“U+FFFE”这样的非字符被定义为 unicode 标准的一部分?据我所知,字节顺序检测(以及处理灵活大小的代码字)取决于编码。

因为编码并不总是提前知道,可能需要动态检测。 U+FFFE用作 BOM 标记以帮助促进这一点。Unicode的早期版本允许U+FFFE用作一个BOM或文本内容内的实际的非破空格字符。这有时会导致模棱两可。因此,较新版本的 UnicodeU+FFFE仅作为 BOM 严格保留,并U+2060 WORD JOINER改为处理不间断空格以避免任何歧义。

话虽如此,在 XML 的上下文中,U+FFFE在任何文本内容中使用都没有意义。整个文档以特定的字符集编码,使用的任何 BOM 都必须出现在 XML 序言之前。XML 规范定义了 XML 文档本身之外的 BOM 处理和字符集检测。所以这就是Char定义排除U+FFFE.

U+FFFF是保留的,并不打算在实践中用于实际内容。所以这就是Char定义排除它的原因。

所以基本上Char定义允许所有 Unicode 代码点减去受限代码点。