【发布时间】:2013-04-16 14:34:51
【问题描述】:
我有一个关于 MySQL 性能的问题。 这些是我的桌子:
(大约 140.000 条记录)
CREATE TABLE IF NOT EXISTS `article` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`label` varchar(256) COLLATE utf8_unicode_ci NOT NULL,
`title` varchar(256) COLLATE utf8_unicode_ci NOT NULL,
`intro` text COLLATE utf8_unicode_ci NOT NULL,
`content` text COLLATE utf8_unicode_ci NOT NULL,
`date` int(11) NOT NULL,
`active` int(1) NOT NULL,
`language_id` int(11) NOT NULL,
`category_id` int(11) NOT NULL,
`indexed` int(1) NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_unicode_ci AUTO_INCREMENT=132911 ;
(大约 400.000 条记录)
CREATE TABLE IF NOT EXISTS `article_category` (
`article_id` int(11) NOT NULL,
`category_id` int(11) NOT NULL
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_unicode_ci;
运行此计数查询:
SELECT SQL_NO_CACHE COUNT(id) as total
FROM (`article`)
LEFT JOIN `article_category` ON `article_category`.`article_id` = `article`.`id`
WHERE `article`.`language_id` = 1
AND `article_category`.`category_id` = '<catid>'
这个查询需要很多资源,所以我想知道如何优化这个查询。 执行后它被缓存了,所以第一次运行后我很好。
运行解释函数:
创建索引后:
ALTER TABLE `article_category` ADD INDEX ( `article_id` , `category_id` ) ;
添加索引并将 LEFT JOIN 更改为 JOIN 后,查询运行速度更快! 感谢这些快速回复:)
我现在使用的查询(我删除了 language_id,因为它不是必需的):
SELECT COUNT(id) as total
FROM (`article`)
JOIN `article_category` ON `article_category`.`article_id` = `article`.`id`
AND `article_category`.`category_id` = '<catid>'
我读过一些关于强制索引的文章,但我认为这不再是必要的了,因为表已经被索引了,对吧?
非常感谢!
马丁
【问题讨论】:
-
向我们展示 EXPLAIN
的结果 -
在
article_category.article_id上添加索引。 -
要么你不应该做
LEFT JOIN,要么你需要在ON子句中测试category_id = <catid>。否则你会过滤掉article_categories中没有匹配的文章。 -
您是否尝试过创建我提到的其他索引...这有什么不同吗?
-
尝试在 language_id 上创建一个简单的索引
标签: mysql optimization join count