Где 1 = 2 вызывается для каждой строки? - PullRequest
5 голосов
/ 12 июля 2010

У меня есть несколько звездочек, которым нужна временная таблица.Чтобы не жестко кодировать типы столбцов (которые являются varchar некоторой длины), поэтому мне не нужно изменять объявления при изменении схемы ссылочной таблицы (т. Е. Поля становятся длиннее), я делаю это (вместо вызова создания таблицы):

select orderId
into #sometmptbl
from orders
where 1=2

Однако, когда вы делаете showplan для этого, на самом деле, кажется, он идет к таблице / индексу:

QUERY PLAN FOR STATEMENT 1 (в строке 1).

STEP 1
    The type of query is CREATE TABLE.

STEP 2
    The type of query is INSERT.
    The update mode is direct.

    FROM TABLE
        orders
    Nested iteration.
    Index : orders_idx1
    Forward scan.
    Positioning at index start.
    Index contains all needed columns. Base table will not be read.
    Using I/O Size 2 Kbytes for index leaf pages.
    With LRU Buffer Replacement Strategy for index leaf pages.
    TO TABLE
        #sometmptbl
    Using I/O Size 2 Kbytes for data pages.

Общая оценочная стоимость ввода-вывода для оператора 1 (в строке 1): 632082.

Означает ли это, что 1 = 2 оценивается для каждой записи в индексе?Есть ли способ сделать это в постоянное время?

Обновление :

Вот фактическая стоимость ввода-вывода после выполнения, так что похоже, что фактические чтениядействительно 0, так что никакого влияния на производительность нет:

Table: orders scan count 0, logical reads: (regular=0 apf=0 total=0), physical reads: (regular=0 apf=0 total=0), apf IOs used=0
Table: #sometmptbl_____00002860018595346 scan count 0, logical reads: (regular=1 apf=0 total=1), physical reads: (regular=0 apf=0 total=0), apf IOs used=0
Total actual I/O cost for this command: 2.
Total writes for this command: 3
0 row(s) affected.

Ответы [ 2 ]

4 голосов
/ 12 июля 2010

Если вы включите статистику io, вы должны увидеть нулевые логические и физические чтения. Он может создать план для сканирования индекса, но, похоже, фактически его не использует.

Я бы рекомендовал НЕ создавать временные таблицы таким способом в производственной среде большого объема. Существуют проблемы с блокировкой системных таблиц, а также незначительное снижение производительности (пробег может отличаться). (также атрибут идентификации столбца переносится во временную таблицу).

В качестве ярлыка - я делаю 1 = 2 в явном tempdb..MyScratchTable, а затем использую RapidSQL (или какой-либо другой инструмент), чтобы сгенерировать DDL из этой временной таблицы.

Если это varchar, не должно быть никаких причин, по которым вы не можете стандартизировать длину столбца по максимальному значению и просто использовать это везде.

0 голосов
/ 12 июля 2010

Что дает select orderId from orders where 1=2?

Возможно, он выбрал индекс для чтения типов данных и т. Д., Тогда как действительно тривиальный запрос (без INTO) должен быть оптимизирован без доступа к таблице / индексу вообще.

...