我在SQL Server 2008 R2上运行简单查询以获取下表:
Id(int,not null)
启用(位,非空)
两列都有单独的索引。
所以当我运行以下查询时:
SELECT Id FROM Entities WHERE Enabled = 1
执行计划显示已完成INDEX_SCAN(由启用列上的CONVERT_IMPLICIT引起)
当我运行另一个查询时:
SELECT Id FROM Entities WHERE Enabled = '1'
或
SELECT Id FROM Entities WHERE Enabled = 'true'
或
SELECT Id FROM Entities WHERE Enabled = CAST(1 AS BIT)
执行计划显示INDEX_SEEK已完成。
由于CONVERT_IMPLICIT会影响更复杂查询的性能,我想知道是什么原因导致SQL Server出现这种情况?
UPD:
如果我跑
SELECT Id FROM Entities WHERE Enabled = 0
然后
SELECT Id FROM Entities WHERE Enabled = 1
执行计划显示INDEX_SEEK。 在这种情况下,我认为SQL Server收集了一些优化统计信息,最后了解到没有理由使用CONVERT_IMPLICIT。但可怜的是,我无法保证我的初始查询将以相反的值执行。
我会很满意我能得到的任何澄清。
答案 0 :(得分:3)
您是否在2000兼容模式下使用数据库?当我阅读here时,如果您使用此兼容模式,您将会遇到此“问题”,但您不会使用2005或2008兼容模式。
所以,如果你需要使用2000兼容模式,你将不得不使用“='1'”比较来避免CONVERT_IMPLICIT,请注意bit和int(或tiny int)之间的类型优先级使得必须“升级”为int。