优化Mysql查询(组和顺序依次为 - >使用索引;使用临时;使用filesort)

时间:2010-11-01 09:47:05

标签: mysql optimization group-by sql-order-by

这是我的SHOW CREATE TABLE tbl:

CREATE TABLE IF NOT EXISTS `msc_pagestats` (
  `id` int(10) unsigned NOT NULL auto_increment,
  `domain` varchar(250) NOT NULL,
  `file` varchar(200) NOT NULL,
  `simbol` varchar(100) NOT NULL,
  `request_time` timestamp NULL default CURRENT_TIMESTAMP,
  `querystring` mediumtext NOT NULL,
  `host` varchar(100) NOT NULL,
  PRIMARY KEY  (`id`),
  KEY `myindex` (`simbol`,`request_time`,`file`,`domain`)
) ENGINE=MyISAM  DEFAULT CHARSET=latin2 AUTO_INCREMENT=248008 ;

所以基本上这个表会根据查询字符串跟踪网站中最常见,最多观看,最多搜索的符号。

我的查询是:

SELECT  `simbol`, count(*) AS requests
 FROM msc_pagestats 
 WHERE 1=1 AND request_time > '20100504000000' 
        AND simbol NOT LIKE ''
 GROUP BY `simbol`
        ORDER BY requests DESC
 LIMIT 0, 15;

此查询已解释:

id  select_type  table  type  possible_keys  key  key_len  ref  rows  Extra

1  SIMPLE  msc_pagestats  index  NULL  myindex  561  NULL  24961  Using where; Using index; Using temporary; Using filesort

因此,查询尝试在最近一小时或今天获取最多的符号。

这是我为了摆脱使用临时和使用filesort而尝试做的事情:

  1. 添加ID作为主键并使用COUNT(id) AS requests代替COUNT(*) AS requests;
  2. 删除where 1=1simbol not like='',但它确实有很大差异;
  3. 添加多索引而不是reqular索引,以前每列ex(KEY(request_time),KEY(文件),KEY(域),KEY(simbol))都有索引。
  4. 我在优化方面不是那么好,所以我已经没有选择了。

    这是我的'mysq_slow_query'文件的转储:

    Query_time:3 Lock_time:0 Rows_sent:15 Rows_examined:220297

    use kmarket;
    SELECT  `simbol`, count(*) AS requests
     FROM msc_pagestats 
     WHERE 1=1 AND request_time > '20100504000000' 
            AND simbol NOT LIKE ''
            GROUP BY `simbol`
     ORDER BY requests DESC
     LIMIT 0, 15;
    

    感谢任何帮助,谢谢:)

1 个答案:

答案 0 :(得分:1)

向运行时计算的字段添加索引没有多大意义,它仍然需要在每次运行时进行排序/索引。

(request_time,simbol)上的索引可能允许优化器更快地排除大量行并减少密钥长度。