简体   繁体   中英

MYSQL: Optimize Order By in Table Sort

I am developing an application for my college's website and I would like to pull all the events in ascending date order from the database. There is a total of four tables:

Table Events1

event_id, mediumint(8), Unsigned
date,     date,                   

Index -> Primary Key (event_id)
Index -> (date)

Table events_users

event_id, smallint(5),  Unsigned
user_id,  mediumint(8), Unsigned

Index -> PRIMARY (event_id, user_id)

Table user_bm

link,    varchar(26)
user_id, mediumint(8)

Index -> PRIMARY (link, user_id)

Table user_eoc

link,    varchar(8)
user_id, mediumint(8)

Index -> Primary (link, user_id)

Query:

EXPLAIN SELECT * FROM events1 E INNER JOIN event_users EU ON E.event_id = EU.event_id
 RIGHT JOIN user_eoc EOC ON EU.user_id = EOC.user_id
 INNER JOIN user_bm BM ON EOC.user_id = BM.user_id
WHERE E.date >= '2013-01-01' AND E.date <= '2013-01-31'
  AND EOC.link = "E690"
  AND BM.link like "1.1%"
ORDER BY E.date

EXPLANATION:

The query above does two things.

1) Searches and filters out all students through the user_bm and user_eoc tables. The "link" columns are denormalized columns to quickly filter students by major/year/campus etc.

2) After applying the filter, MYSQL grabs the user_ids of all matching students and finds all events they are attending and outputs them in ascending order.

QUERY OPTIMIZER EXPLAIN:

id  select_type     table   type      possible_keys     key     key_len     ref rows    Extra
1   SIMPLE  EOC     ref     PRIMARY     PRIMARY     26  const   47  Using where; Using index; Using temporary; Using f...
1   SIMPLE  BM  ref     PRIMARY,user_id-link    user_id-link    3   test.EOC.user_id    1   Using where; Using index
1   SIMPLE  EU  ref     PRIMARY,user_id     user_id     3   test.EOC.user_id    1   Using index
1   SIMPLE  E   eq_ref  PRIMARY,date-event_id   PRIMARY     3   test.EU.event_id    1   Using where

QUESTION:

The query works fine but can be optimized. Specifically - using filesort and using temporary is costly and I would like to avoid this. I am not sure if this is possible because I would like to 'Order By' events by date that have a 1:n relationship with the matching users. The Order BY applies to a joined table.

Any help or guidance would be greatly appreciated. Thank you and Happy Holidays!

Ordering can be done in two ways. By index or by temporary table. You are ordering by date in table Events1 but it's using the PRIMARY KEY which doesn't contain date so in this case the result needs to be ordered in a temporary table.

It is not necessarily expensive though. If the result is small enough to fit in memory it will not be a temporary table on disk, just in memory and that is not expensive.

Neither is filesort. "Using filesort" doesn't mean it will use any file, it just means it's not sorting by index.

So, if your query executes fast you should be happy. If the result set is small it will be sorted in memory and no files will be created.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM