如何在 MySQL 上进行 SQL 区分大小写的字符串比较?
我有一个函数返回五个大小写混合的字符。如果我对此字符串进行查询,无论大小写,它都会返回值。
如何使 MySQL 字符串查询区分大小写?
I have a function that returns five characters with mixed case. If I do a query on this string it will return the value regardless of case.
How can I make MySQL string queries case sensitive?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(12)
使用它来进行区分大小写的查询:
Use this to make a case-sensitive query:
http://dev.mysql.com/doc/refman/5.0 /en/case-sensitivity.html
http://dev.mysql.com/doc/refman/5.0/en/case-sensitivity.html
Craig White 发布的答案有很大的性能损失,
因为它不使用索引。因此,您需要更改表排序规则,就像这里提到的https: //dev.mysql.com/doc/refman/5.7/en/case-sensitivity.html。
或者
最简单的修复,您应该使用 BINARY 值。
例如
VS
一组中的 1 行(0.00 秒)
The answer posted by Craig White has a big performance penalty
because it doesn't use indexes. So, either you need to change the table collation like mention here https://dev.mysql.com/doc/refman/5.7/en/case-sensitivity.html.
OR
Easiest fix, you should use a BINARY of value.
E.g.
VS
1 row in set (0.00 sec)
您可能希望使用 LIKE 或 LIKE BINARY 而不是使用 = 运算符,
它将在其条件中采用“a”而不是“A”
Instead of using the = operator, you may want to use LIKE or LIKE BINARY
It will take 'a' and not 'A' in its condition
在不更改所查询列的排序规则的情况下执行区分大小写的字符串比较的最正确方法是为值<显式指定字符集和排序规则 /strong> (这重要,请阅读下面的原因)与该列进行比较。
为什么不使用
BINARY
?不建议使用 BINARY 运算符,因为它会比较编码字符串的实际字节。如果您比较使用不同字符集编码的两个字符串的实际字节,则两个应被视为相同的字符串可能不相等。例如,如果您有一个使用
latin1
字符集的列,并且您的服务器/会话字符集是utf8mb4
,那么当您将该列与包含重音符号的字符串进行比较时例如“café”,它不会匹配包含相同字符串的行!这是因为在latin1
中,é 被编码为字节0xE9
,但在utf8
中它是两个字节:0xC3A9
。为什么要使用
CONVERT
以及COLLATE
?排序规则必须与字符集匹配。因此,如果您的服务器或会话设置为使用
latin1
字符集,则必须使用collate latin1_bin
,但如果您的字符集是utf8mb4
您必须使用整理utf8mb4_bin
。因此,最可靠的解决方案是始终转换 将值转换为最灵活的字符集,并为该字符集使用二进制排序规则。为什么将
CONVERT
和COLLATE
应用于值而不是列?当您在进行比较之前对列应用任何转换函数时,它会阻止查询引擎使用索引(如果该列存在索引),这可能会显着减慢查询速度。因此,在可能的情况下转换值总是更好。当在两个字符串值之间执行比较并且其中一个具有显式指定的排序规则时,查询引擎将使用显式排序规则,无论它应用于哪个值。
重音敏感度
值得注意的是,MySql 不仅对使用
_ci
排序规则(通常是默认值)的列不区分大小写,而且对重音也不敏感。这意味着'é' = 'e'
。使用二进制排序规则(或BINARY
运算符)将使字符串比较区分重音以及区分大小写。什么是 utf8mb4?
MySQL中的
utf8
字符集是utf8mb3
的别名,它已在最近版本中已弃用,因为它不支持 4 字节字符(这对于编码像The most correct way to perform a case sensitive string comparison without changing the collation of the column being queried is to explicitly specify a character set and collation for the value (this is important, read below why) that the column is being compared to.
Why not use
BINARY
?Using the
BINARY
operator is inadvisable because it compares the actual bytes of the encoded strings. If you compare the actual bytes of two strings encoded using the different character sets two strings that should be considered the same they may not be equal. For example if you have a column that uses thelatin1
character set, and your server/session character set isutf8mb4
, then when you compare the column with a string containing an accent such as 'café' it will not match rows containing that same string! This is because inlatin1
é is encoded as the byte0xE9
but inutf8
it is two bytes:0xC3A9
.Why use
CONVERT
as well asCOLLATE
?Collations must match the character set. So if your server or session is set to use the
latin1
character set you must usecollate latin1_bin
, but if your character set isutf8mb4
you must usecollate utf8mb4_bin
. Therefore the most robust solution is to always convert the value into the most flexible character set, and use the binary collation for that character set.Why apply the
CONVERT
andCOLLATE
to the value and not the column?When you apply any transforming function to a column before making a comparison it prevents the query engine from using an index if one exists for the column, which could dramatically slow down your query. Therefore it is always better to transform the value instead where possible. When a comparison is performed between two string values and one of them has an explicitly specified collation, the query engine will use the explicit collation, regardless of which value it is applied to.
Accent Sensitivity
It is important to note that MySql is not only case insensitive for columns using an
_ci
collation (which is typically the default), but also accent insensitive. This means that'é' = 'e'
. Using a binary collation (or theBINARY
operator) will make string comparisons accent sensitive as well as case sensitive.What is
utf8mb4
?The
utf8
character set in MySQL is an alias forutf8mb3
which has been deprecated in recent versions because it does not support 4 byte characters (which is important for encoding strings like ????). If you wish to use the UTF8 character encoding with MySQL then you should be using theutf8mb4
charset.要在使用 BINARY 之前使用索引,如果您有大型表,可以执行类似的操作。
子查询将产生一个非常小的不区分大小写的子集,然后您可以在其中选择唯一区分大小写的匹配项。
To make use of an index before using the BINARY, you could do something like this if you have large tables.
The subquery would result in a really small case-insensitive subset of which you then select the only case-sensitive match.
您可以像这样使用 BINARY 区分大小写,
不幸的是这个 sql 不能使用索引,您将在依赖该索引的查询上遭受性能损失
幸运的是,我有一些技巧来解决这个问题
You can use BINARY to case sensitive like this
unfortunately this sql can't use index, you will suffer a performance hit on queries reliant on that index
Fortunately, I have a few tricks to solve this problem
以下适用于 MySQL 5.5 或更高版本。
添加到 /etc/mysql/my.cnf
我尝试的所有其他排序规则似乎都不区分大小写,只有“utf8_bin”有效。
此后不要忘记重新启动 mysql:
根据 http://dev.mysql.com /doc/refman/5.0/en/case-sensitivity.html 还有一个“latin1_bin”。
mysql 启动不接受“utf8_general_cs”。 (我将“_cs”读为“区分大小写” - ???)。
Following is for MySQL versions equal to or higher than 5.5.
Add to /etc/mysql/my.cnf
All other collations I tried seemed to be case-insensitive, only "utf8_bin" worked.
Do not forget to restart mysql after this:
According to http://dev.mysql.com/doc/refman/5.0/en/case-sensitivity.html there is also a "latin1_bin".
The "utf8_general_cs" was not accepted by mysql startup. (I read "_cs" as "case-sensitive" - ???).
无需在数据库级别进行任何更改,只需更改 SQL 查询即可工作。
示例 -
"SELECT * FROM where userId = '" + iv_userId + "' AND password = BINARY '" + iv_password + "'";
二进制关键字将区分大小写。
No need to changes anything on DB level, just you have to changes in SQL Query it will work.
Example -
"SELECT * FROM <TABLE> where userId = '" + iv_userId + "' AND password = BINARY '" + iv_password + "'";
Binary keyword will make case sensitive.
出色的!
我与您分享一个比较密码的函数的代码:
Excellent!
I share with you, code from a function that compares passwords:
对于那些希望使用 RLIKE 或 REGEXP 与正则表达式进行区分大小写比较的人,您可以使用
REGEXP_LIKE()
匹配类型c
像这样:For those looking to do case sensitive comparison with a regular expression using
RLIKE
orREGEXP
, you can instead useREGEXP_LIKE()
with match typec
like this:mysql 默认不区分大小写,尝试将语言排序规则更改为
latin1_general_cs
mysql is not case sensitive by default, try changing the language collation to
latin1_general_cs