SQL字符串查询有哪些坑?

本文涉及的产品
Redis 开源版,标准版 2GB
推荐场景:
搭建游戏排行榜
RDS MySQL Serverless 基础系列,0.5-2RCU 50GB
云数据库 RDS MySQL,集群系列 2核4GB
推荐场景:
搭建个人博客
简介: 本文通过创建一个包含不同格式姓名数据的表格,探讨了MySQL中字符排序规则(Collation)的影响。通过使用不区分大小写和空格的查询条件,文章演示了如何获取所有插入的记录,并解释了排序规则中"_ci"、"_cs"及"_bin"的区别。此外,还强调了在数据处理过程中,应考虑大小写敏感性和字符串前后空格的问题,以防导致统计或比较上的错误。最后,提供了Go语言中处理这类问题的方法,如使用`strings.EqualFold()`进行不区分大小写的字符串比较,以及使用`strings.TrimSpace()`去除字符串两端的空白字符。

我们创建如下一张表:

sql

代码解读

复制代码

CREATE TABLE `t` (
  `id` bigint(10) NOT NULL AUTO_INCREMENT,
  `name` varchar(255) DEFAULT NULL COMMENT 'name',
  PRIMARY KEY (`id`)
) ENGINE=InnoDB CHARSET=utf8mb4 COLLATE=utf8mb4_general_ci COMMENT='t'

在这张表我们简单的插入三条数据,插入语句如下:

sql

代码解读

复制代码

INSERT INTO t(name) VALUES("serena "); # 插入尾部带有空格的"serena "
INSERT INTO t(name) VALUES("Serena"); # 插入首字母为大写的"Serena"
INSERT INTO t(name) VALUES("serena"); #  插入"serena"

可以看到,在第一条插入语句,我们插入一个值为"serena "的字符串,注意这个字符串尾部是包含空格的。第二条插入语句中,我们插入首字母为大写的"Serena"。第三个插入语句中,我们则插入值为"serena"的记录。

接下来,我们简单的执行如下

sql

代码解读

复制代码

SELECT * FROM t WHERE `name` = 'serena'

查询结果如下:

从查询结果可以看到,该条SQL语句将刚才我们插入的三条数据都查询了出来,看似简单的SQL语句以及明了的查询结果,我们可以得到:

在建表时,我们使用了COLLATE=utf8mb4_general_ci的排序规则,排序规则(Collation)是比较和排序字符串的一种规则,每个字符集都会有默认的排序规则。

排序规则我们可以通过SHOW CHARSET来进行查看:

排序规则_ci结尾表示不区分大小写(Case Insentive),_cs 表示大小写敏感_bin表示通过存储字符的二进制进行比较

需要注意的是,比较MySQL字符串,默认采用不区分大小的排序规则,我们可以通过一个SQL来进行验证:

另外,在字符串查询的时候,默认SQL语句会帮我们去除掉字段的前后空格,但不会去除字符串空间的空格,这个是需要注意的点,因此上述的查询语句能够将第一条加入的数据记录查询出来。

了解到这两个点后,我们回到开头,为什么说有时候这会是一个坑儿,当我们将这些诸如大小写,包含收尾空格的数据查询到内存时,在代码通过一些字符串比较,计数时,可能会因为大小写,收尾空格等原因,导致统计不准确,或者比较不准确的情况产生,从而导致我们有时候可能需要通过日志打印等方式去逐一排查,排查到最后确实简单的一个字符串排序规则的问题所导致。

go中,我们可以通过库函数来对字符串在内存中进行操作,例如:

  • 字符串比较不区分大小写strings.EqualFold()
  • 去除字符串收尾空格strings.TrimSpace()

go

代码解读

复制代码

package main

import (
    "fmt"
    "strings"
)

func main() {
    str1 := "serena"
    str2 := "Serena"
    str3 := "  serena   "

    // 字符串不区分大小写比较
    fmt.Println(strings.EqualFold(str1, str2)) // true

    // 字符串去除收尾空格
    fmt.Println(strings.TrimSpace(str3)) // serena
}

在学习的过程中,时刻需要把控好看似简单的基础知识,有时候也会成为你排查问题时难以想到的一个问题点。



转载来源:https://juejin.cn/post/7388064351503728655

相关文章
|
4天前
|
SQL 监控 关系型数据库
SQL语句当前及历史信息查询-performance schema的使用
本文介绍了如何使用MySQL的Performance Schema来获取SQL语句的当前和历史执行信息。Performance Schema默认在MySQL 8.0中启用,可以通过查询相关表来获取详细的SQL执行信息,包括当前执行的SQL、历史执行记录和统计汇总信息,从而快速定位和解决性能瓶颈。
|
15天前
|
SQL 存储 缓存
如何优化SQL查询性能?
【10月更文挑战第28天】如何优化SQL查询性能?
60 10
|
9天前
|
SQL 关系型数据库 MySQL
|
23天前
|
SQL 数据库 开发者
功能发布-自定义SQL查询
本期主要为大家介绍ClkLog九月上线的新功能-自定义SQL查询。
|
30天前
|
SQL 移动开发 Oracle
SQL语句实现查询连续六天数据的方法与技巧
在数据库查询中,有时需要筛选出符合特定时间连续性条件的数据记录
|
1月前
|
SQL Java 数据库连接
如何使用`DriverManager.getConnection()`连接数据库,并利用`PreparedStatement`执行参数化查询,有效防止SQL注入。
【10月更文挑战第6天】在代码与逻辑交织的世界中,我从一名数据库新手出发,通过不断探索与实践,最终成为熟练掌握JDBC的开发者。这段旅程充满挑战与惊喜,从建立数据库连接到执行SQL语句,再到理解事务管理和批处理等高级功能,每一步都让我对JDBC有了更深的认识。示例代码展示了如何使用`DriverManager.getConnection()`连接数据库,并利用`PreparedStatement`执行参数化查询,有效防止SQL注入。
85 5
|
1月前
|
SQL 数据挖掘 数据库
SQL查询每秒的数据:技巧、方法与性能优化
id="">SQL查询功能详解 SQL(Structured Query Language,结构化查询语言)是一种专门用于与数据库进行沟通和操作的语言
|
1月前
|
SQL 移动开发 大数据
SQL语句查询连续六天满足条件的记录
在数据库管理和数据分析中,我们经常需要查询符合特定时间范围内连续几天的记录
|
1月前
|
SQL 数据挖掘 关系型数据库
SQL查询次数大于1的记录:高效技巧与方法
在数据库管理中,经常需要统计某些操作的次数,特别是当需要找出哪些记录或值出现的次数超过一定阈值(如大于1次)时
|
1月前
|
SQL 存储 安全
SQL查询数据库:基础概念与操作指南
在数字化时代,数据库已成为信息管理的重要工具之一。作为管理和操作数据库的核心语言,SQL(结构化查询语言)已成为数据管理和查询的关键技能。本文将全面介绍SQL查询数据库的基本概念、语句和操作指南,以帮助初学者快速上手,同时为进阶用户提供有价值的参考。一、数据库与SQL简介数据库是一种存储、管理和检索
40 3