mysql/mariadb - create table column index not working mysql/mariadb - 创建表列索引无效
mysql/mariadb - create table column index not working mysql/mariadb - 创建表列索引无效
我正试图按照以下方式创建我的表格:\n
CREATE TABLE company ( id INT UNSIGNED PRIMARY KEY NOT NULL AUTO_INCREMENT, name TEXT UNIQUE NOT NULL, INDEX(name(20)) );
\n但是出现了如下错误:\nERROR 1170 (42000): BLOB/TEXT列\'name\'在没有键长度的键规范中使用
\n我不确定为什么它不起作用,因为我是按照这里的指南操作的:https://dev.mysql.com/doc/refman/5.5/en/column-indexes.html
在MySQL/MariaDB中创建表时,列索引无法正常工作的问题主要是由以下原因导致的:
1. 对于BLOB和TEXT列,索引必须是前缀索引,因此无法对TEXT列强加UNIQUE约束。也无法将这样的列作为主键或外键约束的一部分。
解决方法有两种常见的方式:
1. 不要使用TEXT列,改用VARCHAR列。
2. 如果确实需要一个长列保持唯一性,可以创建一个第二列,类型为CHAR,COLLATE ascii_bin,为其添加唯一约束,并根据所选择的加密哈希(md5、sha)的base64表示来适当地调整其大小。使用BEFORE INSERT和BEFORE UPDATE触发器,强制该列包含长列的哈希值,从而间接强制唯一性。选择CHAR数据类型是因为所有哈希值长度相同,选择ascii_bin作为排序规则是因为这是base64的最合适排序规则。为什么选择base64?这是一种在存储空间和可读性之间权衡的选择,使用24个字符存储md5哈希值,这是二进制(16个字符,高效)和十六进制(32个字符,低效)编码在存储空间方面的折中。
关于VARCHAR对国际语言的支持程度如何?
据我所知,没有区别。字符集和排序规则决定了这一点,而不是数据类型。如果使用的是默认的latin1字符集,则几乎没有国际支持。可以参考utf8mb4字符集。
另外,对于文本/二进制大对象(TEXT/BLOB),我在某个地方读到可以将前x个字符作为索引,这就是为什么我使用了INDEX(name(20))。我的链接甚至证明了这一点。
.Lau你是对的。该索引将有一个前缀。但是UNIQUE需要创建另一个索引,而不带前缀,这对于BLOB是不支持的。这就是Michael所说的“你关注的是错误的行”。行INDEX(name(20))是完全正确的,如果删除UNIQUE,那么表将被创建。
哦,谢谢,我想我会将它改为VARCHAR。
有点相关的是,如果我想要创建几列的唯一约束,比如UNIQUE (name, other_name),它们是否都需要是VARCHAR类型或其他指定长度的类型?或者它们可以是BLOB/TEXT类型?
它们都需要是VARCHAR,除非你想使用修改过的触发器+加密哈希技术的版本。
请注意,无法对大于某个特定大小的VARCHAR列进行索引(INDEX或UNIQUE)。(大小因MySQL的版本和字符集而异,介于191和3072之间。)
是的,我希望能够得到255,但我尝试了一下,最终只能接受150 🙁