MySQL Order By 不适用于 Concat(enum)

标签 mysql sorting character-encoding enums concatenation

目前我们有一个关于枚举字段中 MySQL 排序顺序的有趣问题。字段枚举条目已按照我们想要的顺序排序。为了保存,我们在它周围添加了一个 CONCAT,因此它会被转换为 char 并按字母顺序排序,正如 MySQL 引用 (MySQL Reference - Enum) 所建议的那样

Make sure that the column is sorted lexically rather than by index number by coding ORDER BY CAST(col AS CHAR) or ORDER BY CONCAT(col).

但这并没有产生预期的结果,所以我们开始进一步调查。看来 order by 语句不适用于 enum 和 concat 函数的组合。我已经编写了以下示例脚本,它应该表明我的观点:

CREATE TABLE test (
  `col1` enum('a','b','c') COLLATE utf8_bin DEFAULT NULL
) ENGINE=MyISAM DEFAULT CHARSET=utf8 COLLATE=utf8_bin;

INSERT INTO test
VALUES ('b'), ('c'), ('a');

SELECT * FROM test; -- b, c, a
SELECT * FROM test ORDER BY col1 ASC; -- a, b, c
SELECT * FROM test ORDER BY CAST(col1 AS CHAR) ASC; -- a, b, c
SELECT * FROM test ORDER BY CAST(col1 AS BINARY) ASC; -- a, b, c
SELECT * FROM test ORDER BY CONCAT(col1) ASC; -- b, c, a - This goes wrong

我目前怀疑整理/编码存在某种问题,但我不确定。我的数据库默认编码也是utf8。 MySQL 版本是 5.6.12,但它似乎可以用 MySQL 5.1 重现。存储引擎是 MyIsam 但它也与内存引擎一起出现。

如有任何帮助,我们将不胜感激。

更新:

问题似乎只在 MySQL 5.6 中和列的排序规则中产生。使用第一个 CREATE TABLE 语句,查询工作正常。

CREATE TABLE test (
  `col1` enum('a','b','c') COLLATE utf8_general_ci DEFAULT NULL
)

第二个他们没有。

CREATE TABLE test (
  `col1` enum('a','b','c') COLLATE utf8_bin DEFAULT NULL
)

表和/或数据库的排序规则似乎不会影响查询。可以在此 SQL Fiddle 中测试查询

最佳答案

奇怪,它在这个 fiddle 里起作用了。你有触发器吗?

http://sqlfiddle.com/#!2/0976a/2

但是,在 5.6 中变得一团糟:

http://sqlfiddle.com/#!9/0976a/1

可能是 Mysql 错误。

更多,如果您以“正确”的顺序在枚举中输入值,它会起作用:

http://sqlfiddle.com/#!9/a3784/1

在文档中:

ENUM values are sorted based on their index numbers, which depend on the order in which the enumeration members were listed in the column specification. For example, 'b' sorts before 'a' for ENUM('b', 'a').

关于MySQL Order By 不适用于 Concat(enum),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/19007583/

相关文章:

windows - 按文件名部分将文本文件排序到文件夹中

java - 为什么 String.endsWith 和 String.startsWith 不一致?

java - 运行 Java 工件时显示 Unicode 字符出现问题,但在 IntelliJ IDEA 中运行时一切正常

MySQL Join 表,如果不满足条件仍然返回 null

php - 警告 : mysqli_select_db() expects parameter 1 to be mysqli, 给出 null

MySQL 查找一行中的重复项

c# - 撇号通过 C# 中的过滤器

java - 无法使私有(private)广播方法起作用

Python 按日期和时间对 CSV 进行排序

linux - 使用 Linux 工具对文件的列进行排序