我有这个复杂的查询,它在大约50ms内产生了3744行。
SELECT
srl.event_id as eid
, srl.race_num as rnum
, bts.boat_id as bid_id
, srl.series_year as yr
, srl.id as id
, IFNULL(rfi.fleet,fleet_def) as flt_old,flt_match,s.series_id as sid
, s.series_year as syr
,IFNULL(ovr_pts,POINTS('4',IFNULL(ovr_place,place),num_start)) as points
FROM
(SELECT en1.boat_id,en1.boat_name,MAX(fleet) as fleet_def FROM entries en1
JOIN series_race_list srl1 ON srl1.event_id=en1.event_id
AND srl1.series_year=en1.race_year
LEFT JOIN entries_race er1 ON en1.boat_id= er1.boat_id
AND srl1.event_id=en1.event_id
AND srl1.series_year =en1.race_year
WHERE srl1.series_id ='3' AND srl1.series_year ='2012'
AND en1.entry_deleted='N'
GROUP BY boat_id) bts
JOIN series_race_list srl LEFT JOIN series as s ON s.series_id=srl.series_id
AND s.series_year =srl.series_year
LEFT JOIN entries as en ON srl.event_id=en.event_id
AND srl.series_year =en.race_year AND bts.boat_id =en.boat_id
LEFT JOIN entries_race er ON er.race_id= srl.event_id AND er.race_num=srl.race_num
AND er.yr = srl.series_year AND bts.boat_id =er.boat_id
LEFT JOIN event_race_info as eri ON eri.race_id= srl.event_id
AND eri.race_num=srl.race_num AND eri.yr = srl.series_year
ANd er.line=eri.line AND status REGEXP 'prelim|final'
LEFT JOIN race_results as rr ON srl.event_id=rr.race_id
AND srl.race_num= rr.race_num AND srl.series_year =rr.yr
AND bts.boat_id= rr.boat_id AND checked_in='Y'
LEFT JOIN race_fleet_info as rfi ON rfi.race_id= srl.event_id
AND rfi.yr=srl.series_year AND srl.race_num= rfi.race_num
AND rfi.fleet=rr.flt AND complete='Y'
LEFT JOIN series_pts_override as spo ON srl.id =spo.id AND en.boat_id =spo.bid
WHERE s.series_id ='3' AND s.series_year ='2012' AND approved ='Y'
抱歉这个长度。正如我所说,这个查询在大约50ms内执行。现在我想使用此数据并对此3744行结果执行查询。我尽快用像
这样的查询来包装它SELECT eid FROM(
......previous query here.....
) data
执行时间从50毫秒到2.5秒哦!
我尝试创建一个临时表,这是一样的。 (实际上这是我的首选方法,因为我需要对此结果集进行一些不同的查询。
在这个网站上阅读我不认为这是一个相关的子查询,但似乎就像一个。
似乎创建别名表的行为是我的问题,因为子查询具有派生表别名,临时表显然是一个表。
如何在没有时间限制的情况下访问这些3744行数据?
如果有帮助我可以弄清楚如何发布解释。
解释更长的查询:
id select_type table type possible_keys key key_len ref rows Extra
1 PRIMARY <derived2> ALL NULL NULL NULL NULL 3744
2 DERIVED s const PRIMARY PRIMARY 5 1
2 DERIVED srl ref series_id,series_id_2 series_id 5 16 Using where
2 DERIVED <derived3> ALL NULL NULL NULL NULL 208 Using join buffer
2 DERIVED en eq_ref PRIMARY,event_id,event_id_2 PRIMARY 9 race_reg_test.srl.event_id,bts.boat_id 1 Using index
2 DERIVED er ref PRIMARY,boat_id,boat_id_2 boat_id_2 5 bts.boat_id 5
2 DERIVED eri eq_ref PRIMARY PRIMARY 13 race_reg_test.srl.event_id,race_reg_test.srl.race_... 1
2 DERIVED rr ref PRIMARY,boat_id boat_id 4 bts.boat_id 9
2 DERIVED rfi eq_ref PRIMARY PRIMARY 31 race_reg_test.srl.event_id,race_reg_test.srl.race_... 1
2 DERIVED spo ref PRIMARY PRIMARY 8 race_reg_test.srl.id,race_reg_test.en.boat_id 1
3 DERIVED srl1 ref series_id,series_id_2 series_id 5 16 Using index; Using temporary; Using filesort
3 DERIVED en1 ref PRIMARY,event_id,event_id_2 PRIMARY 5 race_reg_test.srl1.event_id 11 Using where
3 DERIVED er1 ref boat_id,boat_id_2 boat_id 4 race_reg_test.en1.boat_id 9 Using index
答案 0 :(得分:0)
你说你试过创建一个临时表,我不确定你的意思是否是一个视图。
我将使用该查询创建一个View,然后在View上执行任何必要的查询。
CREATE VIEW massive_query_view AS
SELECT
srl.event_id as eid
, srl.race_num as rnum
, bts.boat_id as bid_id
, srl.series_year as yr
, srl.id as id
, IFNULL(rfi.fleet,fleet_def) as flt_old,flt_match,s.series_id as sid
, s.series_year as syr
,IFNULL(ovr_pts,POINTS('4',IFNULL(ovr_place,place),num_start)) as points
FROM
(SELECT en1.boat_id,en1.boat_name,MAX(fleet) as fleet_def FROM entries en1
JOIN series_race_list srl1 ON srl1.event_id=en1.event_id
AND srl1.series_year=en1.race_year
LEFT JOIN entries_race er1 ON en1.boat_id= er1.boat_id
AND srl1.event_id=en1.event_id
AND srl1.series_year =en1.race_year
WHERE srl1.series_id ='3' AND srl1.series_year ='2012'
AND en1.entry_deleted='N'
GROUP BY boat_id) bts
JOIN series_race_list srl LEFT JOIN series as s ON s.series_id=srl.series_id
AND s.series_year =srl.series_year
LEFT JOIN entries as en ON srl.event_id=en.event_id
AND srl.series_year =en.race_year AND bts.boat_id =en.boat_id
LEFT JOIN entries_race er ON er.race_id= srl.event_id AND er.race_num=srl.race_num
AND er.yr = srl.series_year AND bts.boat_id =er.boat_id
LEFT JOIN event_race_info as eri ON eri.race_id= srl.event_id
AND eri.race_num=srl.race_num AND eri.yr = srl.series_year
ANd er.line=eri.line AND status REGEXP 'prelim|final'
LEFT JOIN race_results as rr ON srl.event_id=rr.race_id
AND srl.race_num= rr.race_num AND srl.series_year =rr.yr
AND bts.boat_id= rr.boat_id AND checked_in='Y'
LEFT JOIN race_fleet_info as rfi ON rfi.race_id= srl.event_id
AND rfi.yr=srl.series_year AND srl.race_num= rfi.race_num
AND rfi.fleet=rr.flt AND complete='Y'
LEFT JOIN series_pts_override as spo ON srl.id =spo.id AND en.boat_id =spo.bid
WHERE s.series_id ='3' AND s.series_year ='2012' AND approved ='Y'
然后,您可以对View执行查询。
SELECT * FROM massive_query_view;
希望加快速度。您可以做的另一件事是检查您的索引。索引使where子句更快但插入更慢。有关更多信息,请查看有关MySQL如何使用索引的MySQL文档:http://dev.mysql.com/doc/refman/5.0/en/mysql-indexes.html。
答案 1 :(得分:0)
一些事情,但我看到的最大的一个是在原始查询中...
boat_id)bts 加入series_race_list srl LEFT JOIN系列为s
bts和srl之间没有“ON”条件,这将导致笛卡尔结果并且可能是你的一个大杀手。对于bts中的每条记录,它在srl中创建一个条目,然后从该产品加入到系列中。从srl到系列是可以的,因为它加在明显有效的标准/键上。
接下来,您有一些不是alias.field的字段,例如最内层查询中的max(fleet)别名为“bts”。另外,为什么MAX(车队)如果按船ID分组,我将其解释为主键并且将是唯一的......船是否会改变它的船队?如果是这样,这是准确的吗?如果你有一个车队表(也有自己的自动序列ID),并且船改变所有权/赞助船(无论如何)到预先存在的车队,从说...车队93到已经有ID的新车在47的文件中尽管47是最新的关系,但是更老的预先存在的ID ...是你真正想要的吗? MAX()?
没有alias.field的其他字段:ovr_pts和ovr_place,放置在字段列表中(以及POINTS()函数是什么... status
在正则表达式,checked_in在比赛结果中,并在竞赛舰队信息,最后在最后的where子句中获得批准。轻微,但可能有助于索引优化。
最后,您的查询在特定的“s.series_id ...和s.series_year ...”上有WHERE子句,但您在查询的前面有一个LEFT-JOIN。这基本上取消了它的左连接组件并将其转换为隐含的INNER JOIN,因为您不允许NULL作为包含的有效选项。
经过一些澄清之后,我甚至可能建议改变一些查询,但我看到的最重要的事情是从一开始......没有“ON”条件加入bts和series_rate_list表。