MySQL留下了连接性能问题

时间:2012-06-20 17:00:38

标签: mysql performance left-join

我一直遇到MySQL(版本5.5)的问题,在许多查询上保持连接性能。在所有情况下,我都能够通过使用联合和子选择重构查询来解决这个问题(我在书中看到了一些例子 High Performance MySQL )。问题是这会导致非常混乱的查询。

以下是两个产生完全相同结果的查询的示例。第一个查询比第二个查询慢大约两个数量级。第二个查询的可读性远低于第一个查询。

据我所知,由于索引错误,这些查询的表现不佳。在我重构查询的所有情况下,它运行得很好。我也试过仔细查看索引并使用提示无济于事。

还有其他人遇到与MySQL类似的问题吗?我应该尝试调整任何服务器参数吗?有没有人找到一种更清洁的方法来解决这类问题?

查询1

select
  i.id,
  sum(vp.measurement * pol.quantity_ordered) measurement_on_order
from items i
left join (vendor_products vp, purchase_order_lines pol, purchase_orders po) on
  vp.item_id = i.id and
  pol.vendor_product_id = vp.id and
  pol.purchase_order_id = po.id and
  po.received_at is null and
  po.closed_at is null
group by i.id

explain:
+----+-------------+-------+--------+-------------------------------+-------------------+---------+-------------------------------------+------+-------------+
| id | select_type | table | type   | possible_keys                 | key               | key_len | ref                                 | rows | Extra       |
+----+-------------+-------+--------+-------------------------------+-------------------+---------+-------------------------------------+------+-------------+
|  1 | SIMPLE      | i     | index  | NULL                          | PRIMARY           | 4       | NULL                                |  241 | Using index |
|  1 | SIMPLE      | po    | ref    | PRIMARY,received_at,closed_at | received_at       | 9       | const                               |    2 |             |
|  1 | SIMPLE      | pol   | ref    | purchase_order_id             | purchase_order_id | 4       | nutkernel_dev.po.id                 |    7 |             |
|  1 | SIMPLE      | vp    | eq_ref | PRIMARY,item_id               | PRIMARY           | 4       | nutkernel_dev.pol.vendor_product_id |    1 |             |
+----+-------------+-------+--------+-------------------------------+-------------------+---------+-------------------------------------+------+-------------+

查询2

select
  i.id,
  sum(on_order.measurement_on_order) measurement_on_order
from (
  (
    select
      i.id item_id,
      sum(vp.measurement * pol.quantity_ordered) measurement_on_order
    from purchase_orders po
    join purchase_order_lines pol on pol.purchase_order_id = po.id
    join vendor_products vp on pol.vendor_product_id = vp.id
    join items i on vp.item_id = i.id
    where
      po.received_at is null and po.closed_at is null
    group by i.id
  )
  union all
  (select id, 0 from items)
) on_order
join items i on on_order.item_id = i.id
group by i.id

explain:
+------+--------------+------------+--------+-------------------------------+--------------------------------+---------+-------------------------------------+------+----------------------------------------------+
| id   | select_type  | table      | type   | possible_keys                 | key                            | key_len | ref                                 | rows | Extra                                        |
+------+--------------+------------+--------+-------------------------------+--------------------------------+---------+-------------------------------------+------+----------------------------------------------+
|  1   | PRIMARY      | <derived2> | ALL    | NULL                          | NULL                           | NULL    | NULL                                | 3793 | Using temporary; Using filesort              |
|  1   | PRIMARY      | i          | eq_ref | PRIMARY                       | PRIMARY                        | 4       | on_order.item_id                    |    1 | Using index                                  |
|  2   | DERIVED      | po         | ALL    | PRIMARY,received_at,closed_at | NULL                           | NULL    | NULL                                |   20 | Using where; Using temporary; Using filesort |
|  2   | DERIVED      | pol        | ref    | purchase_order_id             | purchase_order_id              | 4       | nutkernel_dev.po.id                 |    7 |                                              |
|  2   | DERIVED      | vp         | eq_ref | PRIMARY,item_id               | PRIMARY                        | 4       | nutkernel_dev.pol.vendor_product_id |    1 |                                              |
|  2   | DERIVED      | i          | eq_ref | PRIMARY                       | PRIMARY                        | 4       | nutkernel_dev.vp.item_id            |    1 | Using index                                  |
|  3   | UNION        | items      | index  | NULL                          | index_new_items_on_external_id | 257     | NULL                                | 3380 | Using index                                  |
| NULL | UNION RESULT | <union2,3> | ALL    | NULL                          | NULL                           | NULL    | NULL                                | NULL |                                              |
+------+--------------+------------+--------+-------------------------------+--------------------------------+---------+-------------------------------------+------+----------------------------------------------+

0 个答案:

没有答案
相关问题