Câu trả lời:
Chúng ta sẽ xem xét một vài lý do chi tiết hơn và cũng sẽ nói về một số hạn chế chung của tính năng này.
Đầu tiên, từ: Hạn chế của tính năng Chỉ mục bị thiếu :
- Nó không chỉ định một thứ tự cho các cột được sử dụng trong một chỉ mục.
Như đã lưu ý trong Hỏi & Đáp này: Làm thế nào để SQL Server xác định thứ tự cột chính trong các yêu cầu chỉ mục bị thiếu? , thứ tự của các cột trong định nghĩa chỉ mục được quyết định bởi vị từ Equality vs Bất đẳng thức, và sau đó là vị trí thứ tự cột trong bảng.
Không có dự đoán về sự chọn lọc, và có thể có một thứ tự tốt hơn có sẵn. Đó là công việc của bạn để tìm ra điều đó.
Chỉ số đặc biệt
Thiếu yêu cầu chỉ mục cũng không bao gồm các chỉ mục 'đặc biệt', như:
Các cột khóa Thiếu chỉ mục được tạo từ các cột được sử dụng để lọc kết quả, giống như các cột trong:
Thiếu chỉ mục Các cột được bao gồm được tạo từ các cột theo yêu cầu của truy vấn, giống như các cột trong:
Mặc dù khá thường xuyên, các cột bạn sắp xếp theo hoặc nhóm theo có thể có ích như các cột chính. Điều này quay trở lại một trong những Hạn chế:
- Nó không có ý định tinh chỉnh một cấu hình lập chỉ mục.
Ví dụ: truy vấn này sẽ không đăng ký một yêu cầu chỉ mục bị thiếu, mặc dù việc thêm một chỉ mục trên LastAccessDate sẽ ngăn nhu cầu Sắp xếp (và tràn vào đĩa).
SELECT TOP (1000) u.DisplayName
FROM dbo.Users AS u
ORDER BY u.LastAccessDate DESC;
Điều này cũng không nhóm truy vấn trên Địa điểm.
SELECT TOP (20000) u.Location
FROM dbo.Users AS u
GROUP BY u.Location
Vâng, vâng, nhưng nó tốt hơn là không có gì. Hãy nghĩ về những yêu cầu chỉ số bị thiếu như một đứa bé đang khóc. Bạn biết có một vấn đề, nhưng nó là tùy thuộc vào bạn khi trưởng thành để tìm ra vấn đề đó là gì.
Thư giãn đi Chúng tôi đang tới đó.
Nếu bạn bật TF 2330 , các yêu cầu chỉ mục bị thiếu sẽ không được ghi lại. Để tìm hiểu xem bạn đã bật tính năng này chưa, hãy chạy nó:
DBCC TRACESTATUS;
Xây dựng lại các chỉ mục sẽ xóa các yêu cầu chỉ mục bị thiếu. Vì vậy, trước khi bạn đi Hi-Ho-Silver-Away, xây dựng lại mọi chỉ số, một iota phân mảnh thứ hai lẻn vào, hãy nghĩ về thông tin bạn sẽ xóa mỗi khi bạn làm điều đó.
Dù sao, bạn cũng có thể muốn nghĩ về lý do tại sao phân mảnh chỉ mục của bạn không giúp ích gì. Trừ khi bạn đang sử dụng Cột .
Thêm, xóa hoặc vô hiệu hóa một chỉ mục sẽ xóa tất cả các yêu cầu chỉ mục bị thiếu cho bảng đó. Nếu bạn đang làm việc thông qua một số thay đổi chỉ mục trên cùng một bảng, hãy đảm bảo bạn loại bỏ tất cả chúng trước khi thực hiện bất kỳ.
Nếu một kế hoạch đủ đơn giản và lựa chọn truy cập chỉ mục là đủ rõ ràng và chi phí đủ thấp, bạn sẽ nhận được một kế hoạch tầm thường.
Điều này có nghĩa là không có quyết định dựa trên chi phí cho trình tối ưu hóa để thực hiện.
Qua Paul White :
Các chi tiết về loại truy vấn nào có thể được hưởng lợi từ Kế hoạch tầm thường thay đổi thường xuyên, nhưng những thứ như tham gia, truy vấn con và các vị từ bất bình đẳng thường ngăn chặn tối ưu hóa này.
Khi một kế hoạch là tầm thường, các giai đoạn tối ưu hóa bổ sung sẽ không được khám phá và các chỉ mục bị thiếu không được yêu cầu .
Xem sự khác biệt giữa các truy vấn này và kế hoạch của họ :
SELECT *
FROM dbo.Users AS u
WHERE u.Reputation = 2;
SELECT *
FROM dbo.Users AS u
WHERE u.Reputation = 2
AND 1 = (SELECT 1);
Kế hoạch đầu tiên là tầm thường, và không có yêu cầu nào được hiển thị. Có thể có trường hợp lỗi ngăn các chỉ mục bị thiếu xuất hiện trong các kế hoạch truy vấn; họ thường được đăng nhập đáng tin cậy hơn trong các DMV chỉ mục bị thiếu, mặc dù.
Dự đoán nơi trình tối ưu hóa sẽ không thể sử dụng một chỉ mục một cách hiệu quả ngay cả với một chỉ mục có thể ngăn chúng được ghi lại.
Những thứ thường không phải là SARGable là:
SELECT *
FROM dbo.Users AS u
WHERE ISNULL(u.Age, 1000) > 1000;
SELECT *
FROM dbo.Users AS u
WHERE DATEDIFF(DAY, u.CreationDate, u.LastAccessDate) > 5000
SELECT *
FROM dbo.Users AS u
WHERE u.UpVotes + u.DownVotes > 10000000
DECLARE @ThisWillHappenWithStoredProcedureParametersToo NVARCHAR(40) = N'Eggs McLaren'
SELECT *
FROM dbo.Users AS u
WHERE u.DisplayName LIKE @ThisWillHappenWithStoredProcedureParametersToo
OR @ThisWillHappenWithStoredProcedureParametersToo IS NULL;
Không có truy vấn nào trong số này sẽ đăng ký yêu cầu chỉ mục bị thiếu. Để biết thêm thông tin về những điều này, hãy kiểm tra các liên kết sau:
Lấy chỉ số này:
CREATE INDEX ix_whatever ON dbo.Posts(CreationDate, Score) INCLUDE(OwnerUserId);
Có vẻ ổn cho truy vấn này:
SELECT p.OwnerUserId, p.Score
FROM dbo.Posts AS p
WHERE p.CreationDate >= '20070101'
AND p.CreationDate < '20181231'
AND p.Score >= 25000
AND 1 = (SELECT 1)
ORDER BY p.Score DESC;
Kế hoạch là một Tìm kiếm đơn giản ...
Nhưng vì cột khóa hàng đầu là dành cho vị từ ít chọn lọc, nên cuối cùng chúng tôi sẽ làm nhiều việc hơn chúng ta nên:
Bảng 'Bài viết'. Quét số 13, đọc logic 136890
Nếu chúng tôi thay đổi thứ tự cột khóa chỉ mục, chúng tôi sẽ làm việc ít hơn nhiều:
CREATE INDEX ix_whatever ON dbo.Posts(Score, CreationDate) INCLUDE(OwnerUserId);
Và số lần đọc ít hơn đáng kể:
Bảng 'Bài viết'. Quét số 1, đọc logic 5
Trong một số trường hợp nhất định, SQL Server sẽ chọn tạo một chỉ mục một cách nhanh chóng thông qua một bộ chỉ mục. Khi có một bộ đệm chỉ mục, một yêu cầu chỉ mục bị thiếu sẽ không có. Chắc chắn việc tự thêm chỉ mục có thể là một ý tưởng hay, nhưng đừng tin vào SQL Server giúp bạn tìm ra điều đó.