IS NULL にはインデックスが効くようです

概要

次期システム開発では NULL 許可列を大量に作る予定です。なので、 IS NULL による検索にインデックスが効くかどうかを調べてみました。

昔の Oracle では IS NULL 使うとインデックス効かなかったよね…(いまはどうか知らない。知ってたら誰か教えて。)

内容

テストテーブル作成

CREATE TABLE TESTDB(
	ID int primary key,
	NULLABLE nvarchar(100)
)

テストデータ投入

DECLARE @counter int;
DECLARE @data nvarchar(100);
DECLARE @starttime datetime2
SET @counter = 0;
SET @data = null;
SET @starttime = SYSDATETIME();

WHILE @counter<>99999
	BEGIN
		SET @data = @counter
		IF (DATEDIFF(nanosecond, @starttime,SYSDATETIME())%1000 = 0)
			BEGIN
				SET @data=null
			END
		INSERT INTO TESTDB (ID, NULLABLE) VALUES (@counter, @data);
		SET @counter = @counter+1;
	END

テストデータの状況

SELECT COUNT(*) FROM TESTDB WHERE NULLABLE IS NULL
SELECT COUNT(*) FROM TESTDB WHERE NULLABLE IS NOT NULL

image

インデックス付加

CREATE INDEX TESTIDX ON TESTDB(NULLABLE);

通常検索と実行プラン

SELECT * FROM TESTDB WHERE NULLABLE='88888'

image

Index Seekです。まぁ、当然です。

IS NULL 検索と実行プラン

SELECT * FROM TESTDB WHERE NULLABLE IS NULL

image

IS NULL でもIndex Seek してくれてます。これはありがたい話。

NOT IS NULL 検索と実行プラン

SELECT * FROM TESTDB WHERE NULLABLE IS NOT NULL

image

IS NOT NULL でも Index Seek してくれています。

ちょっと無茶してみた検索と実行プラン

SELECT * FROM TESTDB WHERE ISNULL(NULLABLE, 0)=0

image

さすがにこれは Index Scan になってます。


SQL Server 2008 で確認しました。

しまった。画像取り込みの範囲もう少し横に伸ばして、クエリが見えるようにしておけばよかったな…

コメントを残す