I started to learn MySQL and facing some issues regarding indexing for subquery or join. I have two tables created as following
create table User(id integer, poster integer, PRIMARY KEY (id,poster));
insert into User(id, poster) values(1, 123);
insert into User(id, poster) values(1, 345);
insert into User(id, poster) values(2, 123);
create table Feed(id integer, poster integer, c integer, time integer, PRIMARY KEY(id), INDEX(poster),INDEX(time,c));
insert into Feed(id, poster, c,time) values(1, 123, 0, 2);
insert into Feed(id, poster, c,time) values(2, 123,1,1);
insert into Feed(id, poster, c,time) values(3, 345,2,3);
I initially tried some simple queries like
1. Select poster from User where id =1;
2. Select c from Feed where poster = 1;
3. Select c from Feed where poster in (1,2,3)
The third query explain looks like
SIMPLE Feed NULL ALL poster NULL NULL NULL 3 100.00 Using where; Using filesort
I am not sure why it requires file sort. However after add a composite index INDEX(time,poster,c)to Feed table.Same query will use index
Here is new create table query
create table Feed(id integer, poster integer, c integer, time integer, PRIMARY KEY(id),INDEX(time,poster, c));
Here is explain output with new composite index 1 SIMPLE Feed NULL index NULL time 15 NULL 3 50.00 Using where; Using index
My guess is since order by has higher priority and it is the leftmost index, so we used it first. Then by add poster into composite index, we will be able to still use this composite index to do filter, and finally return c.
Then I tried some subquery
explain SELECT Feed.c from Feed where Feed.poster IN(select poster from User where id =1) order by Feed.time;
Nothing fancy here, I just replace hardcoded (1,2,3) with subquery. I expect to see same explain result, but instead I get
1 SIMPLE User NULL ref PRIMARY,poster PRIMARY 4 const 1 100.00 Using index; Using temporary; Using filesort
1 SIMPLE Feed NULL index NULL time 15 NULL 3 33.33 Using where; Using index; Using join buffer (Block Nested Loop)
I am curious why USER table has Using temporary; Using filesort. I also tried left join it also has same explain output
explain SELECT Feed.c
FROM `Feed`
LEFT JOIN `User` on User.poster = Feed.poster where User.id = 1 order by Feed.time;
Based on my reading, we should avoid using filesort and temporaray file.
How can I optimize my indexing and queries?
Thanks