Mysql HEX函数解码多字节utf8


Mysql HEX function to decode multi-byte utf8

MySQL使用函数HEX(),该函数将把一系列字符转换为十六进制表示。唯一的问题是它假定每个字符是两个字节。这在大多数情况下都很好,但对于utf-8,有时字符的跨度会超过2字节。

例如。0xEFBFBD是用于表示编码错误的三字节字符。当我在数据库中(总共6个字节),在utf8编码的表中,一个接一个地有两个这样的字符时,我尝试SELECT HEX(col1)FROM表。。。,这显示为0xC3AFC2BFC2BD而不是0xEFBFBD。如果我使用php中的查询来选择它,然后在php中将is转换为十六进制,它就会以正确的格式出现。

最好的是MySql函数,它可以解码正确的多字节UTF8。我很惊讶它似乎不存在,我想知道是否有其他人也发现了这种情况,以及可能的解决方法。

我在MySql中找到的最接近答案是:http://forums.mysql.com/read.php?103,375304375660

但这个建议并没有真正的帮助。如果没有人有任何想法,我稍后会发布一个测试用例。

HEX函数返回实际存储的字节;请记住,MySQL很乐意存储混合的字符编码。如果每个字符获得两个字节,则必须用ucs2utf16对值进行编码。要检查编码,可以使用CHARSET函数。

在这种特殊情况下,该列似乎包含쎯슿슽(U+C3AF U+C2BF U+CBD)。肯定还有其他问题让你相信��(U+FFFDU+FFFD)是存储的值。也许您的PHP程序使用ucs2utf16作为连接字符集,然后将获得的文本视为UTF-8?


更新:要获得字符串UTF-8编码的十六进制表示形式(任何字符串,以任何编码*),请使用HEX(CONVERT(string USING utf8))。例如:

set @unknown = char(0xFFFD using ucs2);        -- stored bytes: 'xFF 'xFD
select hex(convert(@unknown using utf8));      -- output: EFBFBD

*)除了没有要从转换的编码的二进制字符串