Производительность хранимых процедур при выборочном обновлении столбцов на основе параметров? - PullRequest
0 голосов
/ 15 июня 2010

Я пытаюсь выяснить, является ли это относительно хорошо работающим T-SQL (это SQL Server 2008). Мне нужно создать хранимую процедуру, которая обновляет таблицу. Процедура принимает столько параметров, сколько столбцов в таблице, и, за исключением столбца PK, все они по умолчанию имеют значение NULL. Тело процедуры выглядит так:

CREATE PROCEDURE proc_repo_update 
    @object_id bigint
    ,@object_name varchar(50) = NULL
    ,@object_type char(2) = NULL
    ,@object_weight int = NULL
    ,@owner_id int = NULL
    -- ...etc
AS
BEGIN
    update
        object_repo
    set
        object_name = ISNULL(@object_name, object_name)
        ,object_type = ISNULL(@object_type, object_type)
        ,object_weight = ISNULL(@object_weight, object_weight)
        ,owner_id = ISNULL(@owner_id, owner_id)
        -- ...etc
    where
        object_id = @object_id

    return @@ROWCOUNT

END

Так что в основном:

Обновлять столбец, только если был предоставлен соответствующий ему параметр, и оставить остальные в покое.

Это работает достаточно хорошо, но поскольку вызов ISNULL вернет значение столбца, если полученный параметр был нулевым, SQL Server каким-то образом оптимизирует это? Это может быть узким местом производительности в приложении, где таблица может быть сильно обновлена ​​(вставка будет необычной, поэтому с производительностью проблем нет). Поэтому я пытаюсь выяснить, как лучше всего это сделать. Есть ли способ обуславливать выражения в столбцах чем-то вроде CASE WHEN или чем-то еще? Таблица будет проиндексирована также для повышения производительности чтения. Это лучший подход? На этом этапе я могу создать выражение UPDATE в коде (например, встроенный SQL) и выполнить его на сервере. Это решило бы мои сомнения относительно производительности, но я бы предпочел оставить это в сохраненном процессе, если это возможно.

Ответы [ 2 ]

1 голос
/ 16 июня 2010

Взгляните на сообщение в блоге Хьюго Корнелиса по адресу http://sqlblog.com/blogs/hugo_kornelis/archive/2007/09/30/what-if-null-if-null-is-null-null-null-is-null.aspx.. Немного загляните к обсуждению COALESCE vs. ISNULL.Если переносимость - будущее соображение, посмотрите на COALESCE.

Однако, с точки зрения производительности , посмотрите на пост в Адаме, ориентированный на производительность в http://sqlblog.com/blogs/adam_machanic/archive/2006/07/12/performance-isnull-vs-coalesce.aspx. ISNULL этоspeedier.

Ваш выбор ...

Кстати, у меня есть несколько SP, которые похожи на ваш пример и не имеют проблем с производительностью при использовании ISNULL.(Будучи немного ленивым, мне нравится печатать 6 против 8 символов, и я немного склонен к дислексии пальцев, ISNULL гораздо проще печатать :-))

1 голос
/ 15 июня 2010

ISNULL - это самый быстрый способ, единственный способ, который вы улучшите, - это если вы передадите NULL или фактическое значение и выполните ISNULL в приложении.

...