почему процесс SQLCLR работает медленнее, чем тот же код на стороне клиента - PullRequest
2 голосов
/ 19 мая 2009

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

Первым шагом в упражнении было просто отсканировать таблицу - именно это и делает код ниже. Проблема заключается в том, что этот код выполняется за 5:45 секунд, однако тот же код, что и консольное приложение (конечно, изменяя строку подключения), выполняется примерно за 44 секунды.

    using (SqlConnection sqlConnection = new SqlConnection("context connection=true"))
    {
        sqlConnection.Open();
        string sqlText = string.Format("select * from {0}", source_table.Value);
        int count = 0;
        using (SqlCommand sqlCommand = new SqlCommand(sqlText, sqlConnection))
        {
            SqlDataReader reader = sqlCommand.ExecuteReader();
            while (reader.Read())
                count++;
            SqlDataRecord record = new SqlDataRecord(new SqlMetaData("rowcount", SqlDbType.Int));
            SqlContext.Pipe.SendResultsStart(record);
            record.SetInt32(0, count);
            SqlContext.Pipe.SendResultsRow(record);
            SqlContext.Pipe.SendResultsEnd();
        }
    }

Однако тот же код (конечно, другая строка подключения) запускается в консольном приложении примерно за 44 секунды (что ближе к тому, что я ожидал на стороне клиента)

Чего мне не хватает на стороне SP, это заставило бы его работать так медленно.

Пожалуйста, обратите внимание: я полностью понимаю, что если мне нужно количество строк, я должен использовать агрегацию количества (*) - это не цель этого упражнения.

Ответы [ 2 ]

2 голосов
/ 19 мая 2009

Тип кода, который вы пишете, очень чувствителен к SQL-инъекциям. Вместо того, чтобы обрабатывать читатель таким, какой вы есть, вы можете просто использовать свойство RecordsActed, чтобы найти количество строк в читателе.

EDIT:

После некоторых исследований вы видите разницу между контекста и обычным соединением. Питер Дебетта написал об этом в блоге и пишет:

"Контекстное соединение написано так, что оно извлекает только строку за раз, поэтому для каждой из 20 миллионов нечетных строк код запрашивал каждую строку отдельно. Однако при использовании неконтекстного соединения запрашивает 8K строк за один раз. "

http://sqlblog.com/blogs/peter_debetta/archive/2006/07/21/context-connection-is-slow.aspx

1 голос
/ 19 мая 2009

Ну, казалось бы, ответ в конце концов в строке подключения.

context connection=true

против

server=(local); database=foo; integrated security=true

По какой-то странной причине, используя «внешнее» соединение, SP запускается почти так же быстро, как консольное приложение (все же не так быстро, заметьте! - 55 секунд)

Конечно, теперь сборка должна быть развернута как Внешняя, а не Безопасная - и это вызывает больше разочарования.

...