我正在使用 ASP.NET 6 MVC 开发一个电子商务网站,MySQL 是我的数据库。 这是我的sp来获取所有产品的数据
CREATE DEFINER=`root`@`localhost` PROCEDURE `product_list`()
BEGIN
SELECT
p.p_code AS ProductCode,
p.p_name AS ProductName,
p.category AS Category,
SUM(pv.stock) AS TotalStock,
i.i_name AS ImageName
FROM
tbl_products p
JOIN
tbl_productvariants pv ON p.p_Id = pv.product_id
JOIN
(
SELECT product_id, i_name
FROM tbl_images
WHERE (product_id, i_id) IN (
SELECT product_id, MIN(i_id)
FROM tbl_images
GROUP BY product_id
)
) i ON p.p_Id = i.product_id
GROUP BY
p.p_Id, p.p_code, p.p_name, p.category, i.i_name
ORDER BY
p.p_Id;
END
当我从 ASP.NET 调用此 sp 时,它显示内存排序错误
我尝试在 my.cnf 文件中进行更改
[mysqld] 排序缓冲区大小 = 2M
这基本上是 MySQL 8.0.23 中的一个 bug/回归。您可以进一步增加缓冲区,但在某些情况下,这也无济于事。
改进查询是首先要尝试的事情,以完全摆脱排序。
tbl_images
上的嵌套子查询可以通过使用窗口函数来改进。您可以将股票计算移动到子查询中,而不是一个巨大的外部GROUP BY
。
SELECT
p.p_code AS ProductCode,
p.p_name AS ProductName,
p.category AS Category,
pv.TotalStock,
i.i_name AS ImageName
FROM
tbl_products p
JOIN
(
SELECT
pv.product_id,
SUM(pv.stock) AS TotalStock
FROM tbl_productvariants pv
) pv ON p.p_Id = pv.product_id
JOIN
(
SELECT
i.product_id,
i.i_name,
ROW_NUMBER() OVER (PARTITION BY i.product_id ORDER BY i.i_id) AS rn
FROM tbl_images i
) i ON p.p_Id = i.product_id AND i.rn = 1
ORDER BY
p.p_Id;
最后,您可以检查查询计划并确保所有表都有正确的索引。我期望以下索引
tbl_products (p_ID) -- primary key
tbl_productvariants (product_id, variant_id, stock)
tbl_images (product_id, i_id, i_name)