Tôi cần một số mẹo để tối ưu hóa truy vấn tìm nạp từ các bảng lớn.Tối ưu hóa truy vấn PostgreSQL với nhiều lần tham gia, sắp xếp theo và giới hạn nhỏ
Trong ví dụ này tôi có 5 bảng:
Brands
- id_brand
- b_name
Products
- id_product
- p_name
- ean
...
- fk_brand
Prod_attributes
- id_prod_att
- size_basic
...
- fk_product
Stores
- id_store
- s_name
...
Stocks
- id_stock
- stock_amount
- fk_prod_att
- fk_store
Tôi cần một truy vấn với danh sách có thứ tự các cổ phiếu, hạn chế, vì vậy đây là cách tiếp cận chung tôi đã sử dụng:
SELECT stores.s_name, stocks.stock_amount, prod_attributes.size_basic,
products.p_name, products.ean, brands.b_name
FROM (stocks
INNER JOIN stores
ON stocks.fk_store = stores.id_store)
INNER JOIN (prod_attributes
INNER JOIN (products
INNER JOIN brands
ON products.fk_brand = brands.id_brand)
ON prod_attributes.fk_product = products.id_product)
ON stocks.fk_prod_att = prod_attributes.id_prod_att
ORDER BY s_name, p_name, size_basic
LIMIT 25 OFFSET 0
này hoạt động nhanh trên các bảng nhỏ, nhưng khi các bảng phát triển truy vấn trở nên rất tốn kém. Với 3,5M hàng trong kho, 300K trong Prod_attributes, 25K Sản phẩm nó thực thi trong hơn 8800ms, điều này không thể chấp nhận được đối với tôi.
Tất cả khóa forgein có chỉ mục và DB đã được phân tích chân không gần đây.
Tôi biết rằng vấn đề nằm trong phần ORDER BY, vì truy vấn không sử dụng chỉ mục và quét tuần tự. Nếu tôi xóa thứ tự thì truy vấn rất nhanh.
Để giải quyết điều này, tôi biết tôi có thể xóa ORDER BY, nhưng đó không phải là tùy chọn khả thi đối với tôi. De-bình thường hóa của DB hoặc quan điểm vật hoá có thể giúp ở đây cũng - một lần nữa tôi muốn tránh điều này nếu có thể.
Tôi có thể làm gì khác để tăng tốc truy vấn này?
GIẢI THÍCH PHÂN TÍCH:
- chậm với thứ tự theo: http://explain.depesz.com/s/AHO
- nhanh chóng mà không cần theo thứ tự theo: http://explain.depesz.com/s/NRxr
Bạn có chỉ mục theo thứ tự theo cột không? –
Xin chào, vâng. Tôi đã thêm các chỉ mục theo thứ tự theo các cột như sau: CREATE INDEX i_p_name TRÊN sản phẩm SỬ DỤNG btree (p_name); Tôi đã thêm chúng dưới dạng các chỉ mục riêng biệt - 1 cho mỗi đơn đặt hàng theo trường. Thứ tự ASC và NULLs LAST. Không có gì thay đổi trong kế hoạch sau khi truy vấn lại. – Lucius
Bạn có chạy phân tích sau khi tạo chỉ mục không? –