记一次字符串末尾空白丢失的排查 → MySQL 是会玩的!

这篇具有很好参考价值的文章主要介绍了记一次字符串末尾空白丢失的排查 → MySQL 是会玩的!。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

开心一刻

  今天答应准时回家和老婆一起吃晚饭,但临时有事加了会班,回家晚了点

  回到家,本以为老婆会很生气,但老婆却立即从厨房端出了热着的饭菜

  老婆:还没吃饭吧,去洗下,来吃饭吧

  我洗好,坐下吃饭,内心感动十分;老婆坐旁边深情的看着我

  老婆:你知道谁最爱你吗

  我毫不犹豫道:你

  老婆:谁最关心你?

  我:你

  老婆:我是谁呀?

  我:我老婆

  老婆:那你以后是不是得对我好点?

  这时电话响了,一看好哥们打过来的,我接了并开了免提

  哥们:楼下洗浴八折,干啥呢?

  我:那个......,在陪我前妻吃口饭

问题背景

  一天,小伙伴找到我,他说他碰到一个很奇怪的问题

  他说:明明表名的入参是 test  ,为什么展示到界面的记录包括 test 这条记录?

  他补充道:会不会是 MyBatis-Plus 做了什么骚操作,把 test  末尾的空格给拿掉了

  我:你直接把 SQL 语句到 MySQL 执行下试试

  结果如下:

记一次字符串末尾空白丢失的排查 → MySQL 是会玩的!

  这看起来不够直观,我移动下光标

记一次字符串末尾空白丢失的排查 → MySQL 是会玩的!

  然后我和小伙伴面面相觑

记一次字符串末尾空白丢失的排查 → MySQL 是会玩的!

环境准备

   MySQL5 、 MySQL8 各准备一个

记一次字符串末尾空白丢失的排查 → MySQL 是会玩的!

记一次字符串末尾空白丢失的排查 → MySQL 是会玩的!

  我们来看下默认情况下,末尾空白的判断情况

   MySQL 5.7.36 如下

记一次字符串末尾空白丢失的排查 → MySQL 是会玩的!

  1 表示 TRUE ,也就是相等

   MySQL 8.0.27 如下

记一次字符串末尾空白丢失的排查 → MySQL 是会玩的!

  0 表示 FALSE ,表示不相等

  这是什么原因,我们继续往下看

字符集与字符序

  比较肯定就需要比较规则, SQL 的比较规则就离不开字符序,字符序又与字符集相关,所以我们一个一个来捋

  字符集

  关于字符集,不是只言片语可以说清楚的,但是大家也不用担心,网上相关资料已经非常多,大家擦亮慧眼去查阅即可

  简单点来说:字符集定义了字符和字符的编码

  有人又问了:字符、字符的编码又是什么?

记一次字符串末尾空白丢失的排查 → MySQL 是会玩的!

  为了方便大家理解,举个简单栗子

    有四个字符:A、B、C、D,这四个字符的编码分别是 A = 0, B = 1, C = 2, D = 3

    这里的字符(A、B、C、D) + 编码(0、1、2、3)就构成了字符集(character set)

   MySQL 支持的字符集有很多,可以通过 SHOW CHARACTER SET; 查看

记一次字符串末尾空白丢失的排查 → MySQL 是会玩的!

   Charset :字符集名

   Description :描述

   Default collation :默认字符序

   Maxlen :每个字符最多字节数

  字符序

  定义了字符的比较规则;字符间的比较按何种规则进行

  一个字符集对应多个字符序,通过 SHOW COLLATION; 可以查看全部的字符序;也可以带条件查具体某个字符集的字符序

记一次字符串末尾空白丢失的排查 → MySQL 是会玩的!

   Default 等于 Yes 表示是默认字符序

  每个字符集都有默认的字符序

  server的字符集与字符序

  当我们创建数据库时,没有指定字符集、字符序,那么server字符集、server字符序就会作为该数据库的字符集、字符序

记一次字符串末尾空白丢失的排查 → MySQL 是会玩的!

  database的字符集与字符序

  指定数据库级别的字符集、字符序

  同一个MySQL服务下的数据库,可以分别指定不同的字符集、字符序

  创建、修改数据库的时候,可以通过 CHARACTER SET 、  COLLATE  指定数据库的字符集、字符序

记一次字符串末尾空白丢失的排查 → MySQL 是会玩的!

  可以通过

记一次字符串末尾空白丢失的排查 → MySQL 是会玩的!

  查看数据库的字符集和字符序

  table的字符集与字符序

  创建、修改表的时候,可以通过 CHARACTER SET 、 COLLATE 指定表的字符集、字符序

记一次字符串末尾空白丢失的排查 → MySQL 是会玩的!

  可以通过

记一次字符串末尾空白丢失的排查 → MySQL 是会玩的!

  查看表的字符序

  column的字符集与字符序

  类型为 CHAR 、 VARCHAR 、 TEXT 的列,可以指定字符集、字符序

记一次字符串末尾空白丢失的排查 → MySQL 是会玩的!

  可以通过

记一次字符串末尾空白丢失的排查 → MySQL 是会玩的!

  查看字段的字符集和字符序

  多个维度指定字符集、字符序的话,粒度越细的优先级越高( column > table > database > server )

  如果细粒度未指定字符集、字符序,那么会继承上一级的字符集,字符序则是上一级字符集的默认字符序

  通常情况下我们一般不会指定 table 、 column 粒度的字符集、字符序

  也就是说,通常情况下 column 的字符集会与 database 的字符集一致,而 column 的字符序则是 database 字符集的默认字符序

空白丢失

  上面讲了那么多,跟空白丢失有什么关系?

  大家先莫急,继续往下看

   MySQL5.7 The CHAR and VARCHAR Types中有这么一段

记一次字符串末尾空白丢失的排查 → MySQL 是会玩的!

  翻译过来就是:

    1、类型是 CHAR 、 VARCHAR 、 TEXT 列的值,会根据列的字符序来比较和排序

    2、所有 MySQL 排序规则的类型都是 PAD SPACE 。这就意味着, CHAR 、 VARCHAR 、 TEXT 类型的值进行比较时,不用考虑任何末尾空格,LIKE 除外

    3、不受 SQL mode 影响,也就是说不管是严格模式,还是非严格模式,都不影响 2 所说的规则

  划重点,记笔记:在 MySQL5.7 及以下( <=5.7 )版本中,排序规则都是 PAD SPACE ,末尾的空格会忽略不考虑

  那如何让末尾空格参与比较了,有三种处理方式

  1、 BINARY ,类似 SELECT 'test' = BINARY 'test '; 

记一次字符串末尾空白丢失的排查 → MySQL 是会玩的!

  2、 LIKE ,类似 SELECT 'test' LIKE 'test '; 

记一次字符串末尾空白丢失的排查 → MySQL 是会玩的!

  3、 LENGTH 函数,类似

记一次字符串末尾空白丢失的排查 → MySQL 是会玩的!

   MySQL8 做了调整,The CHAR and VARCHAR Types 有如下说明

记一次字符串末尾空白丢失的排查 → MySQL 是会玩的!

  翻译过来就是:

    1、类型是 CHAR 、 VARCHAR 、 TEXT 列的值,会根据列的字符序来比较和排序

    2、 MySQL 字符序的 pad 参数的可选值,除了 PAD SPACE ,还增加了 NO PAD 

记一次字符串末尾空白丢失的排查 → MySQL 是会玩的!

    3、对于非二进制字符串( CHAR 、 VARCHAR 、 TEXT ),字符序 pad 参数决定如何去处理字符串末尾的空格

       NO PAD 不会忽略末尾空格,会将其当做其他字符一样对待

       PAD SPACE 会忽略末尾空格, LIKE 除外

       SQL mode 不参与字符串末尾空格的处理

   MySQL8 server 维度的字符集是 utf8mb4 ,对应的默认字符序是: utf8mb4_0900_ai_ci 

记一次字符串末尾空白丢失的排查 → MySQL 是会玩的!

记一次字符串末尾空白丢失的排查 → MySQL 是会玩的!

   Pad_attribute 的值是 NO PAD ,也就是不会忽略字符串末尾的空格

  所以在 MySQL8 中, SELECT 'test' = 'test '; 默认情况下得到的结果是 0

总结

  1、非二进制字符串( CHAR 、 VARCHAR 、 TEXT )比较时,末尾空格的处理跟列的字符序有直接关系

  2、 MySQL5.7 及之前的版本,排序规则的类型都是 PAD SPACE ,会忽略字符串末尾的空格, LIKE 除外

  3、 MySQL8 开始,字符序增加了一个参数 Pad_attribute ,该参数的值不同,对字符串末尾空格的处理方式不同

     NO PAD :字符串末尾的空格会和其他字符一样,不会被忽略

     PAD SPACE :字符串末尾的空格会被忽略, LIKE 除外

  4、如上针对的都是非二进制字符串的排序和比较,而不是储存

参考

  The CHAR and VARCHAR Types

  The CHAR and VARCHAR Types

  再见乱码:5分钟读懂MySQL字符集设置文章来源地址https://www.toymoban.com/news/detail-499191.html

到了这里,关于记一次字符串末尾空白丢失的排查 → MySQL 是会玩的!的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • 【每日挠头算法题(2)】压缩字符串|仅执行一次字符串交换能否使两个字符串相等

    点我直达~ 使用双指针法 大致过程如下: 使用双指针,分别读(read),写(write)指针,读指针不断向后走,当read指针走到最后位置处时,或read和read的下一个位置与当前位置不相等时,说明该read指针走到了某一串相同子串的最后位置处。 此时write指针开始记录具体的字符

    2024年02月08日
    浏览(53)
  • GaussDB(DWS)字符串处理函数返回错误结果集排查

    摘要: 在使用字符串处理函数时,有时会出现非预期结果的场景。在排除使用问题后,应该从encoding和数据本身开始排查。 本文分享自华为云社区《GaussDB(DWS)字符串处理函数返回错误结果集排查》,作者: -CHEN111- 。 在使用字符串处理函数时,有时会出现非预期结果的场景。

    2024年02月03日
    浏览(46)
  • 力扣2085统计出现过一次的公共字符串

    力扣2085统计出现过一次的公共字符串 给你两个字符串数组  words1  和  words2  ,请你返回在两个字符串数组中  都恰好出现一次  的字符串的数目。 思路一. 可以使用两个map分别存储两个字符串数组中所有字符串出现的数量,最后统计两个map中value均为1的字符串。 思路二

    2024年01月16日
    浏览(44)
  • leetcode原题 一次编辑(判定字符串是否只需要一次(或者零次)编辑)

    题目: 字符串有三种编辑操作:插入一个英文字符、删除一个英文字符或者替换一个英文字符。 给定两个字符串,编写一个函数判定它们是否只需要一次(或者零次)编辑。 输入:  first = \\\"pale\\\" second = \\\"ple\\\" 输出: True 解题思路: 本题可以分为以下几种情况来处理: 1. 两个字符串长

    2024年02月13日
    浏览(50)
  • day-07 统计出现过一次的公共字符串

    思路 用哈希表统计words1和words2中各个字符串的出现次数,次数皆为1的字符串符合题意 解题方法 //用于存储words1中各个字符串的出现次数 HashMapString,Integer hashMap1=new HashMap(); //用于存储words2中各个字符串的出现次数 HashMapString,Integer hashMap2=new HashMap(); //如果words1中某个字符串出

    2024年01月16日
    浏览(43)
  • 2085. 统计出现过一次的公共字符串(Java)

    给你两个字符串数组 words1 和 words2 ,请你返回在两个字符串数组中 都恰好出现一次 的字符串的数目。 words1 = [“leetcode”,“is”,“amazing”,“as”,“is”], words2 = [“amazing”,“leetcode”,“is”] 2 解释: “leetcode” 在两个数组中都恰好出现一次,计入答案。 “amazing” 在两个数

    2024年01月17日
    浏览(43)
  • 【Day28】力扣算法(超详细思路+注释) [1790. 仅执行一次字符串交换能否使两个字符串相等 ] [328. 奇偶链表 ][148. 排序链表]

    原题链接:1790. 仅执行一次字符串交换能否使两个字符串相等 题目描述 : 给你长度相等的两个字符串 s1 和 s2 。一次 字符串交换操作的步骤如下:选出某个字符串中的两个下标(不必不同),并交换这两个下标所对应的字符。 如果对 其中一个字符串 执行 最多一次字符串交

    2024年01月22日
    浏览(44)
  • 【LeetCode题解】2645. 构造有效字符串的最少插入数(计算组数+动态规划+考虑相邻字母)+2085. 统计出现过一次的公共字符串(哈希表)+2807. 在链表中插入最大公约数

    2645. 构造有效字符串的最少插入数 方法一:计算组数 1.用count统计,能构成几组abc 2.如果当前字符大于之前字符,说明还在组内,不更新 3.如果当前字符小于等于之前字符,说明不是同一组的abc,组数更新 4.最终返回值:组数*3,再减去原本的字符数,就是要插入的次数 方法二

    2024年04月12日
    浏览(65)
  • 【力扣·每日一题】2085.统计出现过一次的公共字符串(模拟 哈希表 优化 C++ Go)

    题目链接 给你两个字符串数组 words1 和 words2 ,请你返回在两个字符串数组中 都恰好出现一次 的字符串的数目。 输入:words1 = [“leetcode”,“is”,“amazing”,“as”,“is”], words2 = [“amazing”,“leetcode”,“is”] 输出:2 解释: “leetcode” 在两个数组中都恰好出现一次,计入答

    2024年01月21日
    浏览(49)
  • 记一次内存泄漏排查

    最近某项目的服务突然告警,cpu超85%,随后就是服务宕机。交付重启服务后恢复正常但是随后不久又开始告警,特别是白天,严重影响客户业务进行。 1、分析日志 查看日志的过程中发现存在内存溢出(OOM),思考要么存在内存泄漏要么业务上触发了某个接口存在大对象,结

    2023年04月16日
    浏览(52)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包