问答文章1 问答文章501 问答文章1001 问答文章1501 问答文章2001 问答文章2501 问答文章3001 问答文章3501 问答文章4001 问答文章4501 问答文章5001 问答文章5501 问答文章6001 问答文章6501 问答文章7001 问答文章7501 问答文章8001 问答文章8501 问答文章9001 问答文章9501

向Mysql数据库藏储json编码的中文会乱码是什么原因

发布网友 发布时间:2022-05-03 07:26

我来回答

2个回答

懂视网 时间:2022-05-03 11:48

另外,通常不可能在同一网页或数据库中组合不同的编码,因此使用“传统”编码方法来支持多语言页面通常非常困难,所以Unicode协会提供了一个大的,单字节字符集,旨在包括所有需要的世界上任何书写系统,包括古老的脚本(如楔形文字,哥特式和埃及的象形文字)的字符,所以统一字符编码,将其作为Web和操作系统体系结构的基础,并且得到所有主要Web浏览器和应用程序的支持。当前的Unicode字符分为17组编排,每组被称之为一个平面(Plane),所以将字符划分为0-16号的平面,而每平面拥有65536(即216)个代码点即范围区间在0x000到0xFFFF之间,而0号平面就是基本多语言平面(BMP:Basic Mutiingual Plane)。在基本多文本平面上针对每一种文字或者其补充或者其扩展都给出了一个编码范围,比如拉丁文【0000-007F】,拉丁文-补充【0080-00FF】等等。说了这么多,我们只需要记住一点即可:在Unicode字符集中前65536个代码点构成了基本多语言平面简称BMP,BMP中包含了大多常用的字符,另外Unicode字符集还包含了一百万个其他代码点的位置空间,我们称之为补充字符。我们需要区分字符集、编码字符集和编码的概念,字符集或字符串包含可能用于特定目的的字符集,它是支持计算机上的西欧语言所需的字符集,与计算机完全无关,而编码字符集是一组用于该唯一的号码被分配给每个字符的字符,有时候我们将编码字符集也可称作为代码页,编码字符集的单位称为代码点,代码点值表示字符在编码字符集中的位置。例如,Unicode编码字符集中字母á的代码点为十进制225,十六进制表示法为0xE1。而字符编码反映编码字符集被映射到用于在计算机操纵字节的方式。一个字符集可以有多种编码,许多字符编码标准,例如ISO 8859系列中定义的标准,都为给定字符使用单个字节,并且编码是对编码字符集中字符标量位置的直接映射。例如,ISO 8859-1编码字符集中的字母A在第65个字符位置(从零开始),并且使用值为65的字节进行编码并以此在计算机中表示,对于ISO 8859-1而言,这将永远不会再改变,但是,对于Unicode,事情并没有如此简单,尽管Unicode编码字符集中字母á的代码点始终为225(十进制),但在UTF-8中,它在计算机中由两个字节表示,换句话说,在此字符的编码字符集值和编码值之间不是简单的一对一映射,另外,在Unicode中,针对同一字符可以有多种编码的方式。例如,字母á可以用一种编码形式的两个字节表示,而用另一种编码形式的四个字节表示。可以与Unicode一起使用的编码形式称为UTF-8,UTF-16和UTF-32。

技术图片

UTF-8使用1个字节表示ASCII集中的字符,使用2个字节表示其他几个字母块中的字符,使用3个字节表示BMP的其余部分,补充字符使用4个字节。UTF-16对BMP中的任何字符使用2个字节,对补充字符使用4个字节。UTF-32对所有字符使用4个字节。基本多语言平面对应代码点存储的是常用字符,上述针对不同字符在其对应代码点,然后计算出该字符的16进制的字符串,举个栗子,将【好】字进行UTF-8编码看看该字符的字节值和字节数,如下:

  var bytes = Encoding.UTF8.GetBytes("好");

  var hexString = BitConverter.ToString(bytes);

技术图片

到此我们大概了解完了字符编码,接下来我们再次回到上一节的问题,上一节将我姓名作为JSON存储到数据库中去,但是最终获取数据时,将出现乱码,因为其表编码为utf8,最终将表编码修改为utf8mb4才好使,为啥utf8就不行呢?通过上述对utf8的定义最多可以有4个字节,支持补充字符,所以MySQL根本就没有实现标准的utf8编码,换句话说只是部分实现了utf8编码,MySQL中的utf8又名为utf8mb3,也就是一个字符最多可通过3个字节表示且包含BMP字符,而不包含补充字符。所以无论是我的姓还是名虽然是3个字节,但是并非常用BMP字符导致。但是针对列类型为JSON类型,事实是对于获取中文真的会乱码吗?上文我用到的MySQL版本为5.7+,如下:

技术图片

接下来我们利用MySQL 8.0再来进行测试发现不会乱码,创建类和表配置编码如下:

技术图片

 public class t1
 {
 public int id { get; set; }
 public string jdoc { get; set; }
 }

技术图片

 技术图片

 static void Main(string[] args)
 {

  SetDialect(Dialect.MySQL);

  var con = new MySqlConnection(@"Server=localhost;Database=user;Uid=root;Pwd=root;");

  var id = con.Insert(new t1() { jdoc = JsonConvert.SerializeObject(new { Data = "汪鹏" }) });

  var result = con.QueryFirstOrDefault<t1>("select * from t1 where id = @id", new { id });

  Console.ReadKey();
 }

技术图片

随着移动端的兴起,有了表情的出现,所以从MySQL 5.5.3开始,引入utf8mb4字符集每个字符最多可使用4个字节,支持补充字符,对于BMP字符,utf8 [utf8mb3]和utf8mb4具有相同的存储特征:相同的代码值,相同的编码,相同的长度,对于补充字符,utf8 [utf8mb3]根本无法存储该字符,而utf8mb4需要4个字节来存储它,由于utf8 [utf8mb3]根本无法存储字符,因此在utf8 [utf8mb3]列中没有任何补充字符。接下来我们在针对JSON类型配置为utf8编码的情况下,我们来插入表情,此时会发现也是可以的。我们是可以获取对应字符的字节数,比如如下哭笑不得的表情为4个字节:

var emotion = Encoding.UTF8.GetByteCount("??");

技术图片

技术图片

其实针对JSON类型获取数据乱码的情况早就有人提出过相关bug,详见地址《https://bugs.mysql.com/bug.php?id=81677》,不过官方一直没有任何回复,至少通过上述测试出来的结果对于utf8存储表情也可以,到底具体情况咋回事,我们还是看看8.0版本以对utf8编码描述为准,详情请见《https://dev.mysql.com/doc/refman/8.0/en/charset-unicode.html》,对于utf8编码的描述依然还是最多可存储3个字节,如下:

 技术图片

 

别忘记,还有注意:utf8[utf8mb3]字符集已被弃用,并会在将来的MySQL版本中移除,请改用utf8mb4,尽管utf8当前是utf8mb3的别名,但在某些时候utf8将成为对utf8mb4的引用,为避免对utf8的含义含糊不清,请考虑为字符集引用显式指定utf8mb4而不是utf8。所以到此我们已明了,针对8.0版本中的utf8编码虽说最多可支持3个字节,但是,会将utf8成为utf8mb4的引用,如此就不难理解为何上述将表配置为utf8编码时,对于JSON类型的不在常用BMP字符进行数据存储和表情皆没问题。

总结

通过此文对utf8编码的JSON类型的数据出现中文乱码的问题的学习才算告一段落, 原来版本问题使得utf8存在对utf8mb4编码的引用,知其然,知其所以然,嗯,大概是这么个道理。发表博客的好处就在这里,没有批评和指正,哪来的更进一步呢。

MySQL对JSON类型UTF-8编码导致中文乱码探讨

标签:覆盖   字母   乱码   man   获取   存储   系统   ref   doc   

热心网友 时间:2022-05-03 08:56

这个不是乱码,是你进行了编码
声明声明:本网页内容为用户发布,旨在传播知识,不代表本网认同其观点,若有侵权等问题请及时与本网联系,我们将在第一时间删除处理。E-MAIL:11247931@qq.com
圆明新园-明阁地址在哪里? 圆明新园-西洋景区地址在哪里? 新园明园在什么地方 2023年江西普通专升本考试考哪些科目 2023年江西成考专升本需要考些什么科目 2023年江西普通专升本需要考些什么科目 2023年江西专升本需要考些什么科目 北京沸水温度是多少 北京水开的温度是多少 北京市海拔高度和大气压力是多少? 稻花香属于注册商标丛名石板地稻花香米算不算侵权 龙盛稻花香注册过商标吗?还有哪些分类可以注册? 鲍氏稻花香注册过商标吗?还有哪些分类可以注册? 黄金产地稻花香注册过商标吗?还有哪些分类可以注册? 龙辉稻花香注册过商标吗?还有哪些分类可以注册? 鲁花稻花香注册过商标吗?还有哪些分类可以注册? 为什么多人都申请“稻花香”商标都能成功 五常市周城店稻花香商标是否注册了? 美团订的机票到哪里取票呢 美团买的机票取票需要手机号吗? 求稻花香商标分析 在美团网订了飞机票之后飞机票去哪里拿呢? 美团机票如何取 美团上买特价飞机票如何取票 美团订机票怎么取票 百合镇守府药厂汉化不更新了吗 求百合向的游戏 求IG社百合向游戏 《 FLOWERS》汉化硬盘版 最好加上CG クラス全员マヂでゆり百合游戏有汉化的吗? 求百合PC汉化游戏(红线,百合二重奏,少女宫等等) 越多越好!! 团购放什么音乐 初夏狂欢燃爆现场——WEY品牌音乐团购节-武汉站圆满落幕 江苏卫视超级团购总动员广告背景音乐是哪首歌,很熟悉~ 我可以开通电信视频彩铃,来宣传我们小区的水果生鲜团购活动嘛? “你是耀眼的星光”是哪首歌的歌词 “当你握紧我的手,我变遥远的星火”是哪首歌的歌词 Twins 这首专辑是谁唱的? 有没珠江钢琴团购活动呢? 抖音团购活动为什么不能提交 by2有什么好听的歌 哪里能团购演唱会,音乐剧话剧演出的门票 求推荐东莞成人音乐机构 imp3上的团购流程是怎样的? 无锡星音乐ktv团购上面A套餐 B套餐 是要另收费嘛 现在手机视频剪辑app有哪些啊,视频剪辑软件不咕剪辑app怎么样? 不咕剪辑Magicut可以直接使用B站的梗包吗? 游戏排行榜2022手游 手机充不进去电,充电很难怎么办 锰板需要漳火吗 铝镁锰板和铝锰板有什么区别?