在 MySQL 中,数据库对应于数据目录中的目录。数据库中的每个表至少对应于数据库目录中的一个文件(也可能更多,具体取决于存储引擎)。触发器也对应于文件。因此,底层操作系统的区分大小写规则在数据库、表和触发器名称的区分大小写规则中起着一定的作用。这意味着这些名称在 Windows 中不区分大小写,但在大多数 Unix 系统中区分大小写。一个显著的例外是 macOS,它基于 Unix,但使用默认的文件系统类型 (HFS+),该类型不区分大小写。但是,macOS 也支持 UFS 卷,与任何 Unix 一样,UFS 卷区分大小写。请参见 第 1.7.1 节,“MySQL 对标准 SQL 的扩展”。 lower_case_table_names
系统变量也会影响服务器处理标识符大小写敏感性的方式,如本节稍后所述。
尽管数据库、表和触发器名称在某些平台上不区分大小写,但您不应在同一语句中使用不同的方式引用它们。以下语句将不起作用,因为它将同一个表分别称为 my_table
和 MY_TABLE
mysql> SELECT * FROM my_table WHERE MY_TABLE.col=1;
分区、子分区、列、索引、存储例程、事件和资源组名称在任何平台上都不区分大小写,列别名也不区分大小写。
但是,日志文件组的名称区分大小写。这与标准 SQL 不同。
默认情况下,表别名在 Unix 上区分大小写,但在 Windows 或 macOS 上不区分大小写。以下语句在 Unix 上将不起作用,因为它将同一个别名分别称为 a
和 A
mysql> SELECT col_name FROM tbl_name AS a
WHERE a.col_name = 1 OR A.col_name = 2;
但是,同样的语句在 Windows 上是允许的。为了避免此类差异引起的问题,最好采用一致的约定,例如始终使用小写名称创建和引用数据库和表。建议采用此约定以实现最大的可移植性和易用性。
表和数据库名称在磁盘上的存储方式以及在 MySQL 中的使用方式受 lower_case_table_names
系统变量的影响。 lower_case_table_names
可以采用下表所示的值。此变量不会影响触发器标识符的大小写敏感性。在 Unix 上,lower_case_table_names
的默认值为 0。在 Windows 上,默认值为 1。在 macOS 上,默认值为 2。
lower_case_table_names
只能在初始化服务器时配置。禁止在服务器初始化后更改 lower_case_table_names
设置。
值 | 含义 |
---|---|
0 |
表和数据库名称在磁盘上存储时使用 CREATE TABLE 或 CREATE DATABASE 语句中指定的大小写。名称比较区分大小写。如果在文件名不区分大小写的系统(例如 Windows 或 macOS)上运行 MySQL,则不应将此变量设置为 0。如果在不区分大小写的文件系统上使用 --lower-case-table-names=0 强制将此变量设置为 0,并使用不同的大小写访问 MyISAM 表名,则可能会导致索引损坏。 |
1 |
表名在磁盘上以小写形式存储,并且名称比较不区分大小写。MySQL 在存储和查找时会将所有表名转换为小写。此行为也适用于数据库名称和表别名。 |
2 |
表和数据库名称在磁盘上存储时使用 CREATE TABLE 或 CREATE DATABASE 语句中指定的大小写,但 MySQL 在查找时会将它们转换为小写。名称比较不区分大小写。这仅适用于不区分大小写的文件系统!InnoDB 表名和视图名以小写形式存储,与 lower_case_table_names=1 的情况相同。 |
如果您仅在一个平台上使用 MySQL,则通常不需要使用 lower_case_table_names
设置(默认值除外)。但是,如果您想在文件系统大小写敏感性不同的平台之间传输表,则可能会遇到困难。例如,在 Unix 上,您可以有两个名为 my_table
和 MY_TABLE
的不同表,但在 Windows 上,这两个名称被视为相同。为了避免因数据库或表名的大小写而引起的数据传输问题,您有两种选择:
在所有系统上使用
lower_case_table_names=1
。这样做的主要缺点是,当您使用SHOW TABLES
或SHOW DATABASES
时,您不会看到原始大小写的名称。在 Unix 上使用
lower_case_table_names=0
,在 Windows 上使用lower_case_table_names=2
。这将保留数据库和表名的大小写。这样做的缺点是,您必须确保您的语句在 Windows 上始终使用正确的大小写来引用数据库和表名。如果您将语句传输到区分大小写的 Unix 系统,如果大小写不正确,则语句将无法正常工作。例外情况:如果您正在使用
InnoDB
表,并且您试图避免这些数据传输问题,则应该在所有平台上使用lower_case_table_names=1
来强制将名称转换为小写。
如果根据二进制排序规则,对象名称的大写形式相等,则可能会被视为重复的。这适用于游标、条件、过程、函数、保存点、存储例程参数、存储程序局部变量和插件的名称。但这不适用于列、约束、数据库、分区、使用 PREPARE
准备的语句、表、触发器、用户和用户定义变量的名称。
文件系统区分大小写可能会影响 INFORMATION_SCHEMA
表的字符串列中的搜索。有关详细信息,请参见 第 12.8.7 节,“在 INFORMATION_SCHEMA 搜索中使用排序规则”。