2
trace(escape("д"));

将打印“%D0%B4”,这是该字符的正确 URL 编码(相当于“A”的西里尔文)。

但是,如果我要这样做..

myTextArea.htmlText += unescape("%D0%B4");

打印出来的是:

这当然是不正确的。不过,简单地跟踪上面的 unescape 会返回正确的西里尔字符!对于这个 texarea,转义“ä”会返回其 unicode 代码点“%u0434”。

我不确定到底发生了什么事情会搞砸这一切,但是......

Web 编码中的 UTF-16 д 为:%FE%FF%00%D0%00%B4

然而

Web 编码中的 UTF-16 ä 为:%00%D0%00%B4

所以它在开始时用一些东西填充这个值。为什么跟踪会提供与打印到(空)文本区域不同的文本?发生了什么事?

有问题的文本区域没有附加任何奇怪的编码属性,如果这种事情是可能的的话。

4

1 回答 1

4

问题是unescapeescape也可能是一个问题,但在这种情况下它不是罪魁祸首)。这些函数不支持多字节。这escape是做什么的:它在输入字符串中获取一个字节并返回其十六进制表示,并在%前面添加一个。unescape相反。这里的关键点是它们使用字节,而不是字符

你想要的是encodeURIComponent/ decodeURIComponent。两者都使用 utf-8 作为字符串编码方案(flash 到处使用的编码)。请注意,它不是 utf-16(只要涉及闪存,您就不必关心它)。

encodeURIComponent("д"); //%D0%B4
decodeURIComponent("%D0%B4"); // д

现在,如果您想更深入地挖掘,这就是正在发生的事情(这假设您对 utf-8 的工作原理有基本的了解)。

escape("д")

这返回

%D0%B4

为什么?

"ä" 被 flash 当作 utf-8 处理。这个字符的代码点是 0x0434。

二进制:

0000 0100 0011 0100

它适合两个 utf-8 字节,因此它是这样编码的(其中e表示编码位,p表示有效负载位):

1101 0000 1011 0100
eeep pppp eepp pppp 

将其转换为十六进制,我们得到:

0xd0  0xb4

所以,0xd0,0xb4 是一个 utf-8 编码的“ä”。

这是喂给escape. escape看到两个字节,并给你:

%d0%b4

现在,您将其传递给unescape. 但是unescape有点脑残,所以它总是认为一个字节和一个字符是一回事。就unescape目前而言,您有两个字节,因此,您有两个字符。如果您查找 0xd0 和 0xb4 的代码点,您会看到:

0xd0 -> Ð
0xb4 -> ´

因此,unescape返回一个由两个字符组成的字符串,Ð并且´(而不是弄清楚它得到的两个字节实际上只有一个字符,utf-8 编码)。然后,当您分配文本属性时,您并没有真正传递д´ butд`,这就是您在文本区域中看到的内容。

于 2011-03-31T02:42:44.593 回答