MySql中非法混合排序错误

Illegal mix of collations error in MySql

刚刚从上一个问题得到这个答案,它是一种享受!

1
2
3
SELECT username, (SUM(rating)/COUNT(*)) as TheAverage, Count(*) as TheCount
FROM ratings WHERE month='Aug' GROUP BY username HAVING TheCount > 4
ORDER BY TheAverage DESC, TheCount DESC

但当我把这个额外的一点插入它时,它会产生这个错误:

Documentation #1267 - Illegal mix of
collations
(latin1_swedish_ci,IMPLICIT) and
(latin1_general_ci,IMPLICIT) for
operation '='

1
2
3
4
SELECT username, (SUM(rating)/COUNT(*)) as TheAverage, Count(*) as TheCount FROM
ratings WHERE month='Aug'
**AND username IN (SELECT username FROM users WHERE gender =1)**
GROUP BY username HAVING TheCount > 4 ORDER BY TheAverage DESC, TheCount DESC

桌子是:

id, username, rating, month


以下是如何检查哪些列的排序规则错误:

1
2
3
4
5
6
7
SELECT table_schema, table_name, column_name, character_set_name, collation_name

FROM information_schema.columns

WHERE collation_name = 'latin1_general_ci'

ORDER BY table_schema, table_name,ordinal_position;

下面是修复它的查询:

1
ALTER TABLE tbl_name CONVERT TO CHARACTER SET latin1 COLLATE 'latin1_swedish_ci';

链接


检查每个表的排序规则类型,并确保它们具有相同的排序规则。

之后,还要检查操作中使用的每个表字段的排序规则类型。

我也遇到过同样的错误,这套把戏对我很有效。


【MySQL】

在这些(非常罕见的)情况下:

  • 两个真正需要不同排序规则类型的表
  • 值不是来自表,而是来自显式枚举,例如:

    选择1作为数字并集全部选择2并集全部选择3

可以使用CAST或CONVERT比较不同表之间的值:

1
2
3
CAST('my text' AS CHAR CHARACTER SET utf8)

CONVERT('my text' USING utf8)

请参见MySQL网站上的转换和转换文档。


我在phpmyadmin上得到了同样的错误,并且解决方案是否在这里指明了对我有效的方法?

1
ALTER TABLE table CONVERT TO CHARACTER SET utf8 COLLATE utf8_general_ci

非法的排序组合mysql错误另外,我建议使用通用语言而不是瑞典语,因为它是默认语言,除非应用程序使用瑞典语,否则不要使用该语言。


  • 检查users.gender列是否为整数。
  • 试一试:alter table users convert to character set latin1 collate latin1_swedish_ci;

您需要将每个列的排序规则从Latin1_General_Ci更改为Latin1_Swedish_Ci。


简而言之,这个错误是由于MySQL试图对两个具有不同排序规则设置的对象执行操作造成的。如果使设置匹配,则错误将消失。当然,您需要为数据库选择正确的设置,这取决于它将用于什么目的。

在两个非常常见的utf8排序规则之间进行选择时,以下是一些很好的建议:utf8_-general_-ci和utf8_-unicode_-ci之间的区别是什么?

如果您使用的是phpmyadmin,那么可以通过浏览错误消息中提到的表并检查每列的排序规则类型来系统地执行此操作。首先,您应该检查哪个是数据库的整体排序规则设置-phpmyadmin可以告诉您这一点,并在必要时更改它。但是每个表中的每一列都可以有自己的设置。通常你会希望所有这些都匹配。

在一个小的数据库中,这很容易手工完成,而且在任何情况下,如果您完整地阅读了错误消息,它通常会将您指向正确的位置。别忘了查看包含子表的列的"结构"设置。当找到不匹配的排序规则时,可以直接使用phpmyadmin更改它,无需使用查询窗口。然后再次尝试您的操作。如果错误仍然存在,请继续查找!


我想你应该换成UTF8

1
2
3
4
5
6
--set utf8 for connection
SET collation_connection = 'utf8_general_ci'
--change CHARACTER SET of DB to utf8
ALTER DATABASE dbName CHARACTER SET utf8 COLLATE utf8_general_ci
--change CHARACTER SET of table to utf8
ALTER TABLE tableName CONVERT TO CHARACTER SET utf8 COLLATE utf8_general_ci


这里的问题主要是,像这样强制转换字段(字段为varchar)或强制转换(字段为date)


我也有同样的错误,但在我的例子中,主要的问题是我要检查的参数的条件是有一些未知的隐藏字符(+%a0)

当a0转换时,我得到了160,但160超出了db知道的字符范围,这就是为什么数据库不能将其识别为字符的原因。另外,我的表列是varchar

  • 我所做的解决方案是,在运行SQL命令之前,我检查了一些类似的字符,并删除了这些字符。

  • 例如:—preg_replace("/d/","$myparameter");


我在存储过程的WHERE子句中得到了同样的错误。我发现问题出在先前由同一个表/列加载的局部声明变量上。

我把数据转换成单字符类型。


您需要为每个函数中的所有参数设置"utf8"。我的情况是:

在此处输入图像描述


尽可能使用ascii_bin,它几乎可以与任何排序规则匹配。无论如何,用户名很少接受特殊字符。


如果要避免更改语法来解决此问题,请尝试以下操作:

将MySQL更新到5.5或更高版本。

这为我解决了问题。


对于设置为0到1的字段,收集警告也有相同的问题。所有列集合都相同。我们再次尝试更改集合,但没有解决此问题。

最后,我们将字段更新为NULL,然后更新为1,这就解决了收集问题。


1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
SELECT  username, AVG(rating) as TheAverage, COUNT(*) as TheCount
FROM    ratings
        WHERE month='Aug'
        AND username COLLATE latin1_general_ci IN
        (
        SELECT  username
        FROM    users
        WHERE   gender = 1
        )
GROUP BY
        username
HAVING
        TheCount > 4
ORDER BY
        TheAverage DESC, TheCount DESC;


1
HAvING TheCount > 4 AND username IN (SELECT username FROM users WHERE gender=1)

但是为什么我要回答,你没有把我选为正确的答案:)


确保您的MySQL版本支持子查询(4.1+)。接下来,您可以尝试将查询重写为如下内容:

1
2
3
4
5
SELECT ratings.username, (SUM(rating)/COUNT(*)) as TheAverage, Count(*) as TheCount FROM ratings, users
WHERE ratings.month='Aug' and ratings.username = users.username
AND users.gender = 1
GROUP BY ratings.username
HAVING TheCount > 4 ORDER BY TheAverage DESC, TheCount DESC