BLOB/TEXT列'bestilling'用于密钥规范而没有密钥长度

Ism*_*ail 8 mysql text key longtext

我正在尝试建立一个订单系统,但我现在被困住了.在mysql tabel中,我在名为"bestillinger"的列中使用varchar(255),但它只能存储255个字符.所以我搜索了一下,并记得我可以使用longtext或只是文本,但现在当我尝试这样做时,我得到一个错误说:

#1170 - BLOB/TEXT column 'bestilling' used in key specification without a key length
Run Code Online (Sandbox Code Playgroud)

我试图在这里和谷歌搜索,但我没有运气.

我的MySQL表格是:

CREATE TABLE IF NOT EXISTS `bestillinger` (
  `id` int(11) NOT NULL,
  `bestilling` TEXT NOT NULL PRIMARY KEY,
  `accepted` varchar(255) DEFAULT NULL,
  UNIQUE KEY `id_bestilling` (`id`,`bestilling`)
) ENGINE=MyISAM DEFAULT CHARSET=utf8;
Run Code Online (Sandbox Code Playgroud)

我使用UNIQUE KEY因为我在PHP部分使用"ON DUPLICATE KEY UPDATE".但是不要介意.

提前致谢.

jch*_*360 8

您不能将文本设置为主键.Mysql只能索引一些字符,而且类型文本可能太大而无法索引.

看看这里:


Vic*_*Vic 6

根据您上面的定义,以及下面这个答案中的冗长独白,我建议进行以下修订:

CREATE TABLE IF NOT EXISTS `bestillinger` (
  `id` INT UNSIGNED NOT NULL AUTO_INCREMENT PRIMARY KEY,
  `bestilling` TEXT NOT NULL,
  `hashcode` CHAR(32) AS (MD5(bestilling)),  
  `accepted` VARCHAR(255) DEFAULT NULL,
  UNIQUE KEY `id_bestilling` (hashcode,bestilling(333))
) ENGINE=MyISAM DEFAULT CHARSET=utf8;
Run Code Online (Sandbox Code Playgroud)

特定于MySQL,单列索引键的默认最大长度为1000字节长(InnoDB表为767字节,除非您设置了innodb_large_prefix).相同的长度限制适用于任何索引键前缀(CHAR,VARCHAR,TEXT的前N个字符或BINARY,VARBINARY,BLOB的前N个字节).注意字符与字节的区别; 假设UTF-8字符集和每个字符最多3个字节,您可能会在TEXT或VARCHAR列上使用超过333个字符的列前缀索引达到此限制.在实践中,333对我来说往往是最好的.

同样在SQL Server中,所有索引键列的最大总大小都有900字节的限制.

但是只使用你的TEXT的第一个字符作为你的关键,明显的碰撞迫在眉睫.

在接受的答案中,建议使用FULLTEXT索引.FULLTEXT索引是专为文本搜索而设计的,它对INSERT/DELETE的性能不是很好,因为它在列记录的词汇表上维护了一个N-gram并存储了结果向量.如果每个操作都在where子句中使用文本搜索功能,那么这将起作用...但不适用于唯一索引.在'id'上还定义了主键和唯一键,这似乎是多余的,或者我错过了意图.

相反,我建议计算哈希.你是正确的指出有一个机会(生日悖论)会有一个哈希碰撞,所以单独的UNIQUE索引是不够的.如上所述,我们将它与列前缀索引结合起来,以使我们对唯一性有信心.

我收集你的ID列的意图是允许从其他表引用正确的外键.非常正确,但那将是这个表更有用的主键.同样,int(11)指的是列的显示宽度,而不是基础值.我还在'id'上放置了一个未签名的auto_increment,以澄清其对更大受众的角色.

这将我们带到上面提出的设计.