Sample Header Ad - 728x90

Linq compiled query uses clusted index instead of filtered index

1 vote
1 answer
821 views
Given the following table CREATE TABLE Test( Id INT PRIMARY KEY IDENTITY(1, 1), Val INT ) CREATE UNIQUE INDEX UX_Test_Val ON Test(Val) WHERE Val IS NOT NULL DECLARE @i INT = 0 WHILE (@i x.Val == 123).FirstOrDefault(); this gets compiled to something similar to DECLARE @V INT SELECT TOP 1 Id FROM Test WHERE Val = @V OR (Val IS NULL AND @V IS NULL) Seems legit. But I am very disappointed when seeing the clustered index scan in the query plan. The plan looks way better when I remove the second clause. SELECT TOP 1 Id FROM Test WHERE Val = @V This time the plan is a non clustered Index Seek with 1 row read So my first guess is that the filtered index is the evil here and I created a second non-clustered not unique index on the same column CREATE INDEX IX_Test_Val ON Test(Val) This time both statements uses the newly created index and yields to the same index seek plan. Here comes three questions: 1. Why does filtered index has such poor performance in this case? 2. How can I make linq to omit the IS NULL part? 3. Is there a way to enforce unique constrain that allows NULL with just one non filtered index?
Asked by Steve (169 rep)
Mar 6, 2020, 08:40 PM
Last activity: Mar 6, 2020, 09:25 PM