3

我有两张桌子:

类别

category_id         int(10)          UNSIGNED  AUTO_INCREMENT
category_title      varchar(255)

产品

product_id          int(10)          UNSIGNED  AUTO_INCREMENT
product_category    int(10)          UNSIGNED 
product_title       varchar(255)

Columnproduct_category是与category_id. 这是一些数据:

category_id    category_title
-----------    --------------
          3    Cellphone
          4    Motherboard
          5    Monitor

product_id    product_category    product_title
----------    ----------------    -------------
         3    3                   Samsung Galaxy SIII
         4    3                   Apple iPhone 5
         5    3                   HTC One X

如何通过产品数量获取所有类别?

category_id    category_title    products_count
-----------    --------------    --------------
          3    Cellphone         3
          4    Motherboard       9
          5    Monitor           7

我使用了这个查询:

SELECT 
    `category_id` AS  `id`,
    `category_title` AS  `title`,
    COUNT(  `product_id` ) AS  `count` 

FROM  `ws_shop_category` 
    LEFT OUTER JOIN  `ws_shop_product`
        ON  `product_category` =  `category_id` 

GROUP BY  `category_id` 
ORDER BY  `title` ASC 

但它花费的时间太长:(总共 254 个,查询花费了 4.4019 秒)。我怎样才能使这个查询更好?


DESC

在查询之前添加DESC,给我这个结果:

id  select_type table               type    possible_keys   key     key_len ref     rows    Extra
1   SIMPLE      ws_shop_category    ALL     NULL            NULL    NULL    NULL    255     Using temporary; Using filesort
1   SIMPLE      ws_shop_product     ALL     NULL            NULL    NULL    NULL    14320   

显示创建表

CREATE TABLE `ws_shop_product` (
 `product_id` int(10) unsigned NOT NULL AUTO_INCREMENT,
 `product_category` int(10) unsigned DEFAULT NULL,
 `product_title` varchar(255) COLLATE utf8_general_ci DEFAULT NULL,
 PRIMARY KEY (`product_id`)
) ENGINE=MyISAM AUTO_INCREMENT=14499 DEFAULT CHARSET=utf8 COLLATE=utf8_general_ci;

CREATE TABLE `ws_shop_category` (
 `category_id` int(10) unsigned NOT NULL AUTO_INCREMENT,
 `category_title` varchar(255) COLLATE utf8_general_ci DEFAULT NULL,
 PRIMARY KEY (`category_id`)
) ENGINE=MyISAM AUTO_INCREMENT=260 DEFAULT CHARSET=utf8 COLLATE=utf8_general_ci;
4

3 回答 3

2

您的表没有定义任何索引。不过,通过使用以下 statememts 添加索引,它很容易解决:

ALTER TABLE `product` ADD INDEX `product_category` (`product_category`);
ALTER TABLE `category` ADD PRIMARY KEY(category_id);

现在,如果您再次运行查询,DESC应该会显示查询使用键并且应该更快。

于 2013-06-08T07:52:55.217 回答
0

如果您需要高性能,我建议将一个类别中的产品数量存储为 product_category 的列或单独的表中。您可以在每次产品插入/删除时更新相关计数器(手动或使用触发器),也可以使用计划作业每 N 分钟更新一次所有计数器。

您可以在此处找到使用触发器的示例:加速 MySQL 中的行计数

于 2013-06-08T08:15:04.397 回答
0
SELECT ws_shop_category.*, count(ws_shop_product.product_category) as products_count        
from ws_shop_category
left join ws_shop_product
on (ws_shop_category.category_id = ws_shop_product.product_category)
group by
    ws_shop_category.category_id
order by  
    ws_shop_category.category_title asc 
于 2013-06-08T07:37:38.203 回答