我有如下表:我的MySQL索引是否有效?
mysql> describe as_rilevazioni;
+----------------------------+----------+------+-----+---------+----------------+
| Field | Type | Null | Key | Default | Extra |
+----------------------------+----------+------+-----+---------+----------------+
| id | int(11) | NO | PRI | NULL | auto_increment |
| id_sistema_di_monitoraggio | longtext | NO | MUL | NULL | |
| id_unita | longtext | NO | | NULL | |
| id_sensore | longtext | NO | | NULL | |
| data | datetime | NO | | NULL | |
| timestamp | longtext | NO | | NULL | |
| unita_di_misura | longtext | NO | | NULL | |
| misura | longtext | NO | | NULL | |
+----------------------------+----------+------+-----+---------+----------------+
8 rows in set (0.00 sec)
我有以下我的表索引:
mysql> show indexes from as_rilevazioni;
+----------------+------------+----------+--------------+----------------------------+-----------+-------------+----------+--------+------+------------+---------+---------------+
| Table | Non_unique | Key_name | Seq_in_index | Column_name | Collation | Cardinality | Sub_part | Packed | Null | Index_type | Comment | Index_comment |
+----------------+------------+----------+--------------+----------------------------+-----------+-------------+----------+--------+------+------------+---------+---------------+
| as_rilevazioni | 0 | PRIMARY | 1 | id | A | 315865898 | NULL | NULL | | BTREE | | |
| as_rilevazioni | 0 | UNIQUE | 1 | id_sistema_di_monitoraggio | A | 17 | 5 | NULL | | BTREE | | |
| as_rilevazioni | 0 | UNIQUE | 2 | id_unita | A | 17 | 10 | NULL | | BTREE | | |
| as_rilevazioni | 0 | UNIQUE | 3 | id_sensore | A | 145225 | 30 | NULL | | BTREE | | |
| as_rilevazioni | 0 | UNIQUE | 4 | data | A | 315865898 | NULL | NULL | | BTREE | | |
+----------------+------------+----------+--------------+----------------------------+-----------+-------------+----------+--------+------+------------+---------+---------------+
5 rows in set (0.02 sec)
恐怕这些索引效率不高,因为指数的基础上栏“数据”的基数是大数据记录数据! 这些指标加快了我的查询速度,或者它会占用很多空间而没有任何好处?
这是表的定义:
CREATE TABLE `as_rilevazioni` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`id_sistema_di_monitoraggio` longtext NOT NULL,
`id_unita` longtext NOT NULL,
`id_sensore` longtext NOT NULL,
`data` datetime NOT NULL,
`timestamp` longtext NOT NULL,
`unita_di_misura` longtext NOT NULL,
`misura` longtext NOT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `UNIQUE` (`id_sistema_di_monitoraggio`(5),`id_unita`(10),`id_sensore`(30),`data`)
) ENGINE=InnoDB AUTO_INCREMENT=437497044 DEFAULT CHARSET=latin1
我用的主查询是:
select * from as_rilevazioni where id_sistema_di_monitoraggio="<value>" and id_unita="<value>" and id_sensore="<value>" and data>="<date_1>" and data<="<date2>"
这是查询解释说:
mysql> explain select * from as_rilevazioni where id_sistema_di_monitoraggio="235" and id_unita="17" and id_sensore="15" and data >= "2015-01-01 00:00:00" order by data;
+----+-------------+----------------+-------+---------------+--------+---------+------+--------+-------------+
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |
+----+-------------+----------------+-------+---------------+--------+---------+------+--------+-------------+
| 1 | SIMPLE | as_rilevazioni | range | UNIQUE | UNIQUE | 59 | NULL | 285522 | Using where |
+----+-------------+----------------+-------+---------------+--------+---------+------+--------+-------------+
1 row in set (0.00 sec)
这是维数据和索引:
mysql> SELECT concat(table_schema,'.',table_name) tables,
-> concat(round(table_rows/1000000,2),'M') rows,
-> concat(round(data_length/(1024*1024*1024),2),'G') data_size,
-> concat(round(index_length/(1024*1024*1024),2),'G') index_size,
-> concat(round((data_length+index_length)/(1024*1024*1024),2),'G') total_size,
-> round(index_length/data_length,2) index_data_ratio
-> FROM information_schema.TABLES
-> WHERE table_name="as_rilevazioni"
-> ORDER BY total_size DESC;
+------------------------------------+---------+-----------+------------+------------+------------------+
| tables | rows | data_size | index_size | total_size | index_data_ratio |
+------------------------------------+---------+-----------+------------+------------+------------------+
| agriculturalsupport.as_rilevazioni | 317.12M | 19.06G | 10.25G | 29.31G | 0.54 |
+------------------------------------+---------+-----------+------------+------------+------------------+
1 row in set (0.02 sec)
有什么建议吗? 谢谢大家!
我不明白你想要什么。可能的答案是你的问题 - '是'或'否'。看起来一切正确,所以,我的答案是'是'。但是,只有一种方法可以解决你的问题,这是'explain' sql执行结果。请做'解释select ...'并检查'extra'列中的数据。如果只有'使用索引',那就完美了。如果没有'使用索引',看起来你的索引不起作用。 – degr
尝试添加上'id_sistema_di_monitoraggio'一个[多列索引(https://dev.mysql.com/doc/refman/5.7/en/multiple-column-indexes.html),'id_unita','id_sensore'和'数据'。 – sp00m
已有多列索引。 我在原始消息中添加了查询的解释。 – ghes86