我在Amazon Linux上使用MySql 5.6.15。我正在尝试编写一个简单的查询,以按表NAME列的小写版本(其类型为VARCHAR(100))对结果进行排序。该表具有属性
ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_bin
但是请注意,我得到的结果是不同的,唯一不同的是在下面的错误结果中,我得到了另外一列...
mysql> select NAME, ACTIVE, ADDRESS_ID, COUNTRY_ID, CREATED_ON, ORGANIZATION_ID, IMPORT_ADMIN_DATA_FROM_SIS, IMPORT_DATA_FROM_SIS, MDR_NUMBER from organization order by lower(NAME);
+--------------------------------------+--------+------------+------------+---------------------+-----------------+----------------------------+----------------------+------------+
| NAME | ACTIVE | ADDRESS_ID | COUNTRY_ID | CREATED_ON | ORGANIZATION_ID | IMPORT_ADMIN_DATA_FROM_SIS | IMPORT_DATA_FROM_SIS | MDR_NUMBER |
+--------------------------------------+--------+------------+------------+---------------------+-----------------+----------------------------+----------------------+------------+
| Billy Madison Elementary | | NULL | US | 2018-11-29 22:35:57 | 7788 | | 0 | NULL |
| Bradley County Schools | | NULL | US | 2018-11-29 22:35:57 | 8888 | | 0 | NULL |
| Billy Madison Elementary | | NULL | US | 2018-11-29 22:35:57 | 9998 | | 0 | NULL |
当我不要求额外的列时,我得到正确的结果...
mysql> select NAME, ACTIVE, ADDRESS_ID, COUNTRY_ID, CREATED_ON, ORGANIZATION_ID, IMPORT_ADMIN_DATA_FROM_SIS, IMPORT_DATA_FROM_SIS from organization order by lower(NAME);
+--------------------------------------+--------+------------+------------+---------------------+-----------------+----------------------------+----------------------+
| NAME | ACTIVE | ADDRESS_ID | COUNTRY_ID | CREATED_ON | ORGANIZATION_ID | IMPORT_ADMIN_DATA_FROM_SIS | IMPORT_DATA_FROM_SIS |
+--------------------------------------+--------+------------+------------+---------------------+-----------------+----------------------------+----------------------+
| Billy Madison Elementary | | NULL | US | 2018-11-29 22:35:57 | 9998 | | 0 |
| Billy Madison Elementary | | NULL | US | 2018-11-29 22:35:57 | 7788 | | 0 |
| Bradley County Schools | | NULL | US | 2018-11-29 22:35:57 | 8888 | | 0 |
这到底是怎么回事?如何返回按小写名称排序的结果?
编辑:通过运行“ SHOW CREATE TABLE”来创建表语句...
| organization | CREATE TABLE `organization` (
`ID` varchar(32) COLLATE utf8_bin NOT NULL,
`STATE_ID` varchar(10) COLLATE utf8_bin DEFAULT NULL,
`ORGANIZATION_ID` varchar(32) COLLATE utf8_bin NOT NULL,
`COUNTRY_ID` varchar(10) COLLATE utf8_bin NOT NULL,
`NAME` varchar(100) COLLATE utf8_bin NOT NULL,
`ORGANIZATION_TYPE_ID` varchar(2) COLLATE utf8_bin NOT NULL,
`PARENT_ORGANIZATION_ID` varchar(32) COLLATE utf8_bin DEFAULT NULL,
`USER_ENTERED` tinyint(4) DEFAULT '0',
`SAMPLE_ORGANIZATION` tinyint(4) DEFAULT '0',
`IMPORT_DATA_FROM_SIS` tinyint(1) NOT NULL DEFAULT '0',
`USE_EXTERNAL_AUTHENTICATION` tinyint(1) NOT NULL DEFAULT '0',
`ADDRESS_ID` varchar(32) COLLATE utf8_bin DEFAULT NULL,
`LTI_REFERER_DOMAIN` varchar(32) COLLATE utf8_bin DEFAULT NULL,
`URL_ID` varchar(32) COLLATE utf8_bin DEFAULT NULL,
`CREATED_ON` timestamp NULL DEFAULT CURRENT_TIMESTAMP,
`MDR_NUMBER` varchar(32) COLLATE utf8_bin DEFAULT NULL,
`ACTIVE` bit(1) DEFAULT b'1',
`IMPORT_ADMIN_DATA_FROM_SIS` bit(1) DEFAULT b'0',
`USE_EXTERNAL_AUTH_FOR_ADMINS` bit(1) DEFAULT b'0',
PRIMARY KEY (`ID`),
UNIQUE KEY `UK_ORGANIZATION` (`ORGANIZATION_ID`),
KEY `FK1_ORGANIZATION` (`COUNTRY_ID`),
KEY `FK3_ORGANIZATION` (`ORGANIZATION_TYPE_ID`),
KEY `FK2_ORGANIZATION` (`PARENT_ORGANIZATION_ID`),
KEY `FK_ORGANIZATION` (`ADDRESS_ID`),
KEY `FK5_ORGANIZATION` (`URL_ID`),
CONSTRAINT `FK1_ORGANIZATION` FOREIGN KEY (`COUNTRY_ID`) REFERENCES `cb_country` (`ID`) ON DELETE CASCADE ON UPDATE NO ACTION,
CONSTRAINT `FK2_ORGANIZATION` FOREIGN KEY (`PARENT_ORGANIZATION_ID`) REFERENCES `organization` (`ID`) ON DELETE CASCADE ON UPDATE NO ACTION,
CONSTRAINT `FK3_ORGANIZATION` FOREIGN KEY (`ORGANIZATION_TYPE_ID`) REFERENCES `cb_org_type` (`ID`) ON DELETE CASCADE ON UPDATE NO ACTION,
CONSTRAINT `FK5_ORGANIZATION` FOREIGN KEY (`URL_ID`) REFERENCES `sb_url` (`ID`) ON UPDATE NO ACTION,
CONSTRAINT `FK_ORGANIZATION` FOREIGN KEY (`ADDRESS_ID`) REFERENCES `cb_address` (`ID`) ON UPDATE NO ACTION
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_bin |
答案 0 :(得分:0)
您实际上并不需要在order by语句中使用较低的值,这是MySQL的默认设置。除此之外,我从未见过这样的错误...也许是要删除订单中的较低功能,看看是否能解决问题...
从MySQL文档开始: 与所有其他比较操作一样,在字符类型列上的排序通常以不区分大小写的方式执行。这意味着除了大小写相同之外,其他列均未定义顺序。您可以像这样使用BINARY强制对列进行区分大小写的排序:ORDER BY BINARY col_name。
答案 1 :(得分:0)
您发布的SQL是正确的。我创建了一个SQL fiddle来尝试使用问题中的数据来重现您的问题,但是效果很好。 Comment out the order by
clause,您会在问题中看到不好的结果。
有时UTF8字符串看起来相同,但是却不相同。您是否已验证
select * from organization where name = "Billy Madison Elementary"
返回您期望的2行?
如果NAME
是相同的,则没有一种排序不会使它们彼此相邻。 NAME
上唯一与您看到的结果一致的排序是,所有3行都具有相同的NAME
值。在某些情况下,您可能会遇到这种情况,其中字符串全部都转换为整数值,所有名称都转换为零,但是即使那样,我仍希望结果的顺序在您的问题的两个查询之间保持一致。
有很多晦涩的查询可以被截断的方式,我想您最可能看到的解释是,第一个查询中的order by
子句没有到达服务器。您如何发出查询?您是否尝试过使用(不同的)交互方式来运行查询?如果您保留MDR_NUMBER
列但在查询中忽略了IMPORT_ADMIN_DATA_FROM_SIS
列怎么办?
您可以使用sqlfiddle.com重现该问题吗?如果是这样,请将链接添加到您的问题。
答案 2 :(得分:0)
在这里列选择不应该成为问题。我不确定“布拉德利县学校”是如何出现的。但是,如果大小写敏感是问题,则可以使用BINARY运算符。它强制字符串比较是逐字节而不是逐字符。查找更多详细信息here