MySQL中这种查询的最佳索引是什么?
这是我的桌子:MySQL中这种查询的最佳索引是什么?,mysql,database,indexing,Mysql,Database,Indexing,这是我的桌子: create table page_relation ( relationid int primary key, userid int, pageid int, registryid int ); 让我们想象一下,我想多次获得一个用户每页的所有注册表的计数。 下面是我将要运行的查询: select count(*) as register_count from page_relation where userid = 10 group
create table page_relation (
relationid int primary key,
userid int,
pageid int,
registryid int
);
让我们想象一下,我想多次获得一个用户每页的所有注册表的计数。
下面是我将要运行的查询:
select count(*) as register_count
from page_relation
where userid = 10
group by pageid;
我需要帮助找出什么是最好的索引,以加快这一quind的查询
到目前为止,我尝试在(userid,pageid)
上使用复合索引,希望MySQL将索引用于group by,但不幸的是,当我使用EXPLAIN时,额外的信息不包含任何“using index for group by”信息,只说我正在使用索引,我正在使用where。这是否意味着我的索引不用于排序
从理论上讲,如果这个索引是聚集的,它不会工作吗?我在想一个B-树,聚集和稀疏索引会很好地完成这项工作。。。老实说,我甚至希望它是一个覆盖指数,但我真的不知道它是不是
以下是我的解释:
# id, select_type, table, type, possible_keys, key, key_len, ref, rows, Extra
1, SIMPLE, page_relation, ref, idx_count, idx_count, 4, const, 60, Using where; Using index
仅用于执行此查询的最佳索引是什么
感谢您抽出时间。使用以下两种方法中的任何一种都可以满足要求:
select userid,pageid,count(*) as register_count
from page_relation
where userid = 10
group by userid,pageid;
INDEX(userid), INDEX(pageid)
注意:对于复合键,MySQL按照声明的顺序使用索引。例如,复合键(userid,pageid)必须使用字段userid
进行过滤或分组,否则将忽略索引
第一种方法的好处是,它只能引用一个索引。索引数越少,写入效率越高。考虑到空间和时间的复杂性,我建议您选择1st方法进行BTREE
索引
假设:pageid
字段不唯一
注意:如果在任何版本的MySQL中都没有使用索引,请在select子句中保留groupby
字段 可使用以下两种方法中的任何一种来满足要求:
INDEX(userid, pageid)
复合索引覆盖(userid,pageid)
查询:
select userid,pageid,count(*) as register_count
from page_relation
where userid = 10
group by userid,pageid;
两个索引-一个在userid上,另一个在pageid上
查询:查询将保持与问题中提到的相同
INDEX(userid), INDEX(pageid)
注意:对于复合键,MySQL按照声明的顺序使用索引。例如,复合键(userid,pageid)必须使用字段userid
进行过滤或分组,否则将忽略索引
第一种方法的好处是,它只能引用一个索引。索引数越少,写入效率越高。考虑到空间和时间的复杂性,我建议您选择1st方法进行BTREE
索引
假设:pageid
字段不唯一
注意:如果在任何版本的MySQL中都没有使用索引,请在select子句中保留groupby
字段
INDEX(userid, pageid)
是唯一要添加的rational索引
EXPLAIN
在指示索引(pageid
在本例中)是被使用还是被忽略时是相当蹩脚的。您可以尝试EXPLAIN FORMAT=JSON SELECT…
,看看这是否澄清了问题
INDEX(userid), INDEX(pageid)
没有那么有用。它可以使用其中一个,但不能同时使用两个。它可能会使用(userid),但这本质上并不比复合索引更好,甚至更糟
这个问题本身令人费解。你有多行吗?如果没有,请通过
删除组。如果是这样,您是否应该将pageid
添加到SELECT
列表中
这其中的大部分,我都在我的书里
另一个谜题。。。这是一个“关系”表;你的意思是用户ID和页面ID之间的“多对多”映射吗?或者别的什么。在many:many表中,通常需要双向执行,因此索引必须双向执行。另外,代理id
也没有用,因为主键(userid,pageid)
是有保证的。(看我的食谱。)
我将其升级到主键
,可以提高效率
我太沉迷于“如果”了;回答我的一些问题;然后我会继续闲逛
是唯一要添加的rational索引
EXPLAIN
在指示索引(pageid
在本例中)是被使用还是被忽略时是相当蹩脚的。您可以尝试EXPLAIN FORMAT=JSON SELECT…
,看看这是否澄清了问题
INDEX(userid), INDEX(pageid)
没有那么有用。它可以使用其中一个,但不能同时使用两个。它可能会使用(userid),但这本质上并不比复合索引更好,甚至更糟
这个问题本身令人费解。你有多行吗?如果没有,请通过
删除组。如果是这样,您是否应该将pageid
添加到SELECT
列表中
这其中的大部分,我都在我的书里
另一个谜题。。。这是一个“关系”表;你的意思是用户ID和页面ID之间的“多对多”映射吗?或者别的什么。在many:many表中,通常需要双向执行,因此索引必须双向执行。另外,代理id
也没有用,因为主键(userid,pageid)
是有保证的。(看我的食谱。)
我将其升级到主键
,可以提高效率
我太沉迷于“如果”了;回答我的一些问题;然后我将继续漫谈。非常有趣,我也在某个地方面对它,等待核心DBA的回答!顺便说一句,一个表只能有一个聚集索引,而您的表聚集索引被主键占用。您也可以尝试强制索引!如果删除主键索引会怎么样?是的,索引的强度取决于它的基数。PK的基数为1。你做得再好不过了@Hytool checkout此索引(userid,pageid)
是一个覆盖索引,如