B.4.7 MySQL 中的已知问题

本节列出了最新版本的 MySQL 中的已知问题。

有关特定于平台的问题的信息,请参阅第 2.1 节“常规安装指南”第 28.5 节“调试和移植 MySQL”中的安装和移植说明。

已知以下问题:

  • IN的子查询优化不如=有效。

  • 即使使用lower_case_table_names=2(这使 MySQL 能够记住用于数据库和 table 名的大小写),MySQL 也不会记住用于函数DATABASE()或各种日志中的数据库名的大小写(在不区分大小写的系统上)。

  • 删除FOREIGN KEY约束在复制中不起作用,因为该约束在副本上可能具有其他名称。

  • REPLACE(和带有REPLACE选项的LOAD DATA)不会触发ON DELETE CASCADE

  • 如果您不使用全部并且仅使用DISTINCT列 table 中的那些列,则DISTINCTORDER BYGROUP_CONCAT()内部不起作用。

  • 在十进制或字符串列中插入大整数值(介于 263 和 264-1 之间)时,它会作为负值插入,因为该数字是在带符号整数上下文中求值的。

  • 使用基于语句的二进制日志记录,源服务器将已执行的查询写入二进制日志。这是一种非常快速,紧凑且有效的日志记录方法,在大多数情况下均可完美运行。但是,如果查询的设计方式使得数据修改是不确定的(通常不是推荐的做法,甚至是复制之外的做法),则源和副本上的数据可能会变得不同。

For example:

当且仅当前面的查询中没有ORDER BY子句保证确定性 Sequences 时

例如,对于没有ORDER BY插入...选择SELECT可能以不同的 Sequences 返回行(这导致行具有不同的排名,因此在AUTO_INCREMENT列中获得不同的数字),这取决于源上优化器的选择。和副本。

仅在以下情况下,查询在源和副本上的优化有所不同:

  • 该 table 使用与复制源不同的存储引擎存储在源上。 (可以在源和副本上使用不同的存储引擎.例如,如果副本具有较少的可用磁盘空间,则可以在源上使用InnoDB,但可以在副本上使用MyISAM.)

    • 源和副本上的 MySQL 缓冲区大小(key_buffer_size等)不同。

    • 源和副本运行不同的 MySQL 版本,并且这些版本之间的优化器代码不同。

这个问题也可能影响使用 mysqlbinlog | mysql **进行数据库还原。

避免此问题的最简单方法是在上述非确定性查询中添加ORDER BY子句,以确保始终以相同 Sequences 存储或修改行。使用基于行或混合的日志记录格式也可以避免此问题。

  • 如果未使用启动选项指定文件名,则日志文件名基于服务器主机名。如果将主机名更改为其他名称,要保留相同的日志文件名,必须显式使用诸如--log-bin=old_host_name-bin之类的选项。参见第 5.1.6 节“服务器命令选项”。或者,重命名旧文件以反映您的主机名更改。如果这些是二进制日志,则必须编辑二进制日志索引文件,并在那里也修复二进制日志文件的名称。 (复制副本上的中继日志也是如此.)

  • mysqlbinlog不会删除LOAD DATA语句后剩余的临时文件。参见第 4.6.7 节“ mysqlbinlog-处理二进制日志文件的 Util”

  • RENAME不适用于TEMPORARYtable 或MERGEtable 中使用的 table。

  • 使用SET CHARACTER SET时,不能在数据库,table 和列名称中使用翻译的字符。

  • 您不能在喜欢...逃生中将_%ESCAPE一起使用。

  • 比较数据值时,服务器仅使用前max_sort_length个字节。这意味着,如果值仅在前max_sort_length个字节之后不同,则不能在GROUP BYORDER BYDISTINCT中可靠地使用这些值。要解决此问题,请增加变量值。 max_sort_length的默认值为 1024,可以在服务器启动时或在运行时更改。

  • 数值计算是使用BIGINTDOUBLE(通常都是 64 位长)进行的。您获得哪种精度取决于功能。一般规则是位功能以BIGINT精度执行,IF()ELT()BIGINTDOUBLE精度执行,其余函数以DOUBLE精度执行。如果无符号的 long long 值解析为大于 63 位(9223372036854775807),而不是位字段,则应尽量避免使用它们。

  • 一个 table 中最多可以包含 255 个ENUMSET列。

  • MIN()MAX()和其他聚合函数中,MySQL 当前通过它们的字符串值而不是字符串在集合中的相对位置来比较ENUMSET列。

  • UPDATE语句中,列从左到右更新。如果引用更新的列,则获取的是更新后的值,而不是原始值。例如,以下语句将KEY增加2,而不是1

mysql> UPDATE tbl_name SET KEY=KEY+1,KEY=KEY+1;
  • 您可以在同一查询中引用多个临时 table,但是不能多次引用任何给定的临时 table。例如对于以下不起作用:
mysql> SELECT * FROM temp_table, temp_table AS t2;
ERROR 1137: Can't reopen table: 'temp_table'
  • 当您在联接中使用“隐藏”列时,优化器处理DISTINCT的方式与未使用时不同。在联接中,隐藏列被计为结果的一部分(即使未显示),而在常规查询中,隐藏列不参与DISTINCT比较。

例如:

SELECT DISTINCT mp3id FROM band_downloads
       WHERE userid = 9 ORDER BY id DESC;

and

SELECT DISTINCT band_downloads.mp3id
       FROM band_downloads,band_mp3
       WHERE band_downloads.userid = 9
       AND band_mp3.id = band_downloads.mp3id
       ORDER BY band_downloads.id DESC;

在第二种情况下,您可能在结果集中得到两个相同的行(因为隐藏的id列中的值可能不同)。

请注意,这仅适用于结果中没有ORDER BY列的查询。

  • 如果对返回空集的查询执行PROCEDURE,则在某些情况下PROCEDURE不会转换列。

  • 创建类型为MERGE的 table 不会检查基础 table 是否为兼容类型。

  • 如果使用ALTER TABLEUNIQUE索引添加到MERGEtable 中使用的 table,然后在MERGEtable 上添加普通索引,则如果 table 中有旧的非UNIQUE键,则 table 的键 Sequences 会有所不同。这是因为ALTER TABLEUNIQUE索引放在普通索引之前,以便能够尽早检测到重复的键。