3

我在产品表上有以下索引:(product_t,productid,forsale)。MySQL手册说:

GROUP BY 只命名构成索引最左前缀的列,而不命名其他列。 http://dev.mysql.com/doc/refman/5.0/en/group-by-optimization.html

当我执行以下查询时

SELECT z.product_t, COUNT(z.productid)
FROM xcart_products z
JOIN xcart_products_lng w ON z.productid = w.productid
AND w.code =  'US'
WHERE z.forsale =  'Y'
group by z.product_t

因此使用最左边的索引字段(product_t),执行时间仍然很长:

+-----------+--------------------+
| product_t | COUNT(z.productid) |
+-----------+--------------------+
| B         |                  4 |
| C         |              10521 |
| D         |                  1 |
| F         |                 16 |
| G         |                363 |
| J         |                 16 |
| L         |                749 |
| M         |                 22 |
| O         |                279 |
| P         |               5304 |
| S         |                 22 |
| W         |                662 |
+-----------+--------------------+
12 rows in set (0.81 sec)

当我使用整个索引(product_t、productid、forsale)时,执行时间非常快(0.005 秒)。我应该如何更改它以使查询更快?

在此处输入图像描述

我认为可以通过使用半连接以某种方式改进查询...但是我不确定如何...

4

3 回答 3

3

减速可能与 GROUP BY 子句无关。尝试分别为 w.code 和 z.forsale 添加索引。

MySQL Profiling也可以帮助你的努力

于 2012-12-22T17:32:35.367 回答
0

最明显的答案是仅为 product_t 创建一个新索引。你能创建新的索引吗?

于 2012-12-22T16:54:11.233 回答
0

谢天谢地,我找到了一种提高速度的方法。我确实有另一个表,其中定义了所有 product_t。那里的每个 product_t 还使用“代码”字段(指定每个 product_t 的翻译)。在此表中,我还在 product_t 和代码上定义了一个索引。通过将查询更改为:

SELECT z.product_t, COUNT(z.productid)
FROM xcart_products z
JOIN xcart_products_lng w ON z.productid = w.productid
JOIN xcart_products_product_t_lng p ON z.product_t = p.product_t
AND p.code =  'US'
WHERE z.forsale =  'Y'
group by p.product_t,p.code

我设法将速度提高到 0.10 秒。它更快的原因是因为分组依据现在是在整个索引上完成的。其次,将 where code='US' 从大 products_lng 表替换为小 product_t_lng 表。我认为这是最有效的查询......

mysql> SELECT z.product_t, COUNT( z.productid )
        -> FROM xcart_products z
        -> JOIN xcart_products_lng w ON z.productid = w.productid
        -> JOIN xcart_products_product_t_lng p ON z.product_t = p.product_t
        -> AND p.code =  'US'
        -> WHERE z.forsale =  'Y'
        -> GROUP BY p.product_t, p.code
        -> ;
    +-----------+----------------------+
    | product_t | COUNT( z.productid ) |
    +-----------+----------------------+
    | B         |                    4 |
    | C         |                10521 |
    | F         |                   16 |
    | G         |                  363 |
    | L         |                  749 |
    | M         |                   22 |
    | O         |                  279 |
    | P         |                 5304 |
    | S         |                   22 |
    | W         |                  662 |
    +-----------+----------------------+
    10 rows in set (0.14 sec)
于 2012-12-22T18:44:57.747 回答