我有两张桌子: 表1:
CREATE TABLE `lk_transaction_types` (
`transactionTypeID` int(10) unsigned NOT NULL AUTO_INCREMENT,
`isActive` tinyint(2) unsigned NOT NULL,
`code` varchar(8) NOT NULL,
`description` varchar(150) NOT NULL,
`isInbound` tinyint(2) unsigned NOT NULL DEFAULT '1',
`isOutbound` tinyint(2) unsigned NOT NULL DEFAULT '1',
PRIMARY KEY (`transactionTypeID`)
) ENGINE=InnoDB AUTO_INCREMENT=32 DEFAULT CHARSET=utf8;
表2:
CREATE TABLE `ediLoad` (
`loadID` int(10) unsigned NOT NULL AUTO_INCREMENT,
`processID` int(10) unsigned NOT NULL,
`success` tinyint(2) unsigned NOT NULL DEFAULT '0',
`transactionTypeID` tinyint(2) unsigned DEFAULT NULL,
`escoID` int(10) unsigned DEFAULT NULL,
`ldcID` int(10) unsigned DEFAULT NULL,
`commodityType` tinyint(3) unsigned NOT NULL DEFAULT '0',
`filename` varchar(150) NOT NULL,
`loadDate` datetime NOT NULL,
`processed` tinyint(2) unsigned NOT NULL DEFAULT '0',
`processedDate` datetime DEFAULT NULL,
`dataApplied` tinyint(2) unsigned NOT NULL DEFAULT '0',
`dataAppliedDate` datetime DEFAULT NULL,
`errorID` tinyint(3) unsigned DEFAULT NULL,
`error` tinyint(2) unsigned DEFAULT '0',
`warning` tinyint(2) unsigned DEFAULT '0',
PRIMARY KEY (`loadID`),
KEY `idx_processID` (`processID`,`transactionTypeID`,`escoID`),
KEY `idx_escoID` (`escoID`),
KEY `idx_filename` (`success`,`filename`),
KEY `idx_bulk` (`processed`,`loadDate`),
KEY `idx_loadDate` (`loadDate`) USING BTREE
) ENGINE=InnoDB AUTO_INCREMENT=35086005 DEFAULT CHARSET=utf8;
尝试运行简单查询时,它不使用lk_transaction_types表上的主键:
SELECT COUNT(0)
FROM edi.ediLoad l
INNER JOIN edi.lk_transaction_types lk
ON lk.transactionTypeID = l.transactionTypeID
WHERE l.escoID = 2
AND lk.isActive = 1
AND lk.isInbound = 1;
查询非常慢。所以我运行解释
EXPLAIN SELECT COUNT(0)
FROM edi.ediLoad l
INNER JOIN edi.lk_transaction_types lk
ON lk.transactionTypeID = l.transactionTypeID
WHERE l.escoID = 2
AND lk.isActive = 1
AND lk.isInbound = 1;
返回
id select_type table partitions type possible_keys key key_len ref rows filtered Extra
1 SIMPLE lk NULL ALL PRIMARY NULL NULL NULL 31 3.23 Using where
1 SIMPLE l NULL ref idx_escoID idx_escoID 5 const 71580 10.00 Using where
这似乎是一个简单的查询,主键上有一个连接。为什么不使用主键?我甚至尝试在连接中添加'FORCE INDEX FOR JOIN(PRIMARY)',它仍然不使用主键。任何帮助都会很棒。谢谢!
答案 0 :(得分:0)
详细说明@Uueerdo在上述评论中所说的内容:在这种情况下,MySQL无法使用 idx_processID 索引,因为 transactionTypeID 是第二个索引中的列,第一个列( processID )不是where语句的一部分。
如果仅使用 transactionTypeID 添加新密钥,则会使用该密钥。
来自https://dev.mysql.com/doc/refman/5.7/en/multiple-column-indexes.html:
MySQL可以对测试所有内容的查询使用多列索引 索引中的列,或仅测试第一列的查询, 前两列,前三列,依此类推。如果你指定 索引定义中的列顺序正确,单个 复合索引可以加快几种查询的速度 表