Theo Chương 9 (Trình phân tích cú pháp và Trình tối ưu hóa), Trang 172 của cuốn sách Tìm hiểu nội bộ MySQL của Sasha Pachev
Dưới đây là phân tích đánh giá của một truy vấn như các tác vụ sau:
- Xác định các khóa nào có thể được sử dụng để truy xuất các bản ghi từ các bảng và chọn khóa tốt nhất cho mỗi bảng.
- Đối với mỗi bảng, hãy quyết định xem quét bảng có tốt hơn không khi đọc trên khóa. Nếu có nhiều bản ghi khớp với giá trị khóa, các ưu điểm của khóa sẽ giảm và quá trình quét bảng trở nên nhanh hơn.
- Xác định thứ tự các bảng sẽ được nối khi có nhiều hơn một bảng trong truy vấn.
- Viết lại các mệnh đề WHERE để loại bỏ mã chết, giảm các tính toán không cần thiết và thay đổi các ràng buộc bất cứ nơi nào có thể để mở đường cho việc sử dụng các khóa.
- Loại bỏ các bảng không sử dụng từ tham gia.
- Xác định xem các phím có thể được sử dụng cho
ORDER BY
và GROUP BY
.
- Cố gắng đơn giản hóa các truy vấn con, cũng như xác định mức độ kết quả của chúng có thể được lưu trữ.
- Hợp nhất các khung nhìn (mở rộng tham chiếu khung nhìn dưới dạng macro)
Trên cùng một trang, nó nói như sau:
Trong thuật ngữ tối ưu hóa MySQL, mỗi truy vấn là một tập hợp các phép nối. Thuật ngữ tham gia được sử dụng ở đây rộng hơn trong các lệnh SQL. Một truy vấn chỉ có một bảng là một phép nối suy biến. Mặc dù chúng ta thường không nghĩ rằng đọc các bản ghi từ một bảng như một phép nối, các cấu trúc và thuật toán tương tự được sử dụng với các phép nối thông thường hoạt động hoàn hảo để giải quyết truy vấn chỉ với một bảng.
TIẾNG VIỆT
Do có các khóa hiện tại, số lượng dữ liệu và biểu hiện của truy vấn, MySQL Joins đôi khi có thể làm mọi việc vì lợi ích của chúng tôi (hoặc để lấy lại cho chúng tôi) và đưa ra kết quả mà chúng tôi không mong đợi và không thể giải thích nhanh chóng.
Tôi đã viết về sự khó chịu này trước đây
bởi vì Trình tối ưu hóa truy vấn MySQL có thể loại bỏ một số khóa nhất định trong quá trình đánh giá truy vấn.
Nhận xét của @ Phil giúp tôi xem cách đăng câu trả lời này (+1 cho nhận xét của @ Phil)
Nhận xét của @ ypercube (+1 cho bài viết này cũng vậy) là phiên bản rút gọn của bài đăng của tôi vì Trình tối ưu hóa truy vấn của MySQL là nguyên thủy. Thật không may, nó phải được kể từ khi nó liên quan đến các công cụ lưu trữ bên ngoài.
PHẦN KẾT LUẬN
Đối với câu hỏi thực tế của bạn, Trình tối ưu hóa truy vấn MySQL sẽ xác định số liệu hiệu suất của từng truy vấn khi hoàn thành
- đếm hàng
- chọn phím
- mát xa tập kết quả không liên tục
- Ồ vâng, thực hiện THAM GIA
Bạn có thể sẽ phải ép buộc thứ tự thực hiện bằng cách viết lại (tái cấu trúc) truy vấn
Đây là truy vấn đầu tiên bạn đưa ra
select count(*)
from table1 a
join table2 b
on b.key_col=a.key_col
where b.tag = 'Y';
Hãy thử viết lại để đánh giá WHERE trước
select count(*)
from table1 a
join (select key_col from table2 where tag='Y') b
on b.key_col=a.key_col;
Điều đó chắc chắn sẽ thay đổi kế hoạch GIẢI THÍCH. Nó có thể tạo ra kết quả tốt hơn hoặc xấu hơn.
Tôi đã từng trả lời một câu hỏi trong StackOverflow nơi tôi đã áp dụng kỹ thuật này. EXPLAIN là khủng khiếp nhưng hiệu suất là động lực. Nó chỉ hoạt động vì có các chỉ mục chính xác hiện tại và việc sử dụng GIỚI HẠN trong truy vấn con .
Cũng như giá cổ phiếu, khi nói đến Truy vấn và cố gắng thể hiện chúng, các hạn chế được áp dụng, kết quả có thể thay đổi và hiệu suất trong quá khứ không biểu thị cho kết quả trong tương lai.