#sql #sql-server-2005
#sql #sql-server-2005
Вопрос:
В настоящее время я автоматически создаю скрипт с помощью программы, которая копирует файлы из одного места в другое, и раньше я делал следующее:
UPDATE d
SET Path = t.Path
FROM dbo.tableOperation d
JOIN (VALUES (1, 'Path 1'),
(2, 'Path 2')) t (IdRegister, Path) ON t.IdRegister = d.IdRegister
И на SQL Server 2008 R2 (v10.50.1600) все работало нормально, но я обнаружил некоторые проблемы с синтаксисом при попытке отобразить предполагаемый план выполнения скрипта на сервере, я должен обновить данные (9.0.50000). В ошибке конкретно указано
Неправильный синтаксис рядом с ключевым словом ‘VALUES’
Мне нужно обновлять десятые доли тысяч строк за раз, как я могу это сделать?
Ответ №1:
Возможно, вам придется переключиться с VALUES()
на UNION ALL
для 2005 (также будет работать в 2008). Но имейте в виду, что поддержка SQL Server 2005 закончилась несколько лет назад. (Я имею в виду, это настолько старое, что я забыл VALUES()
, что его там не было.) Время двигаться дальше?
UPDATE d
SET Path = t.Path
FROM dbo.tableOperation AS d
INNER JOIN
(
SELECT 1,'Path 1'
UNION ALL SELECT 2,'Path 2'
) AS t (IdRegister, Path)
ON t.IdRegister = d.IdRegister;
Комментарии:
1. Я бы с удовольствием обновил его, но на самом деле это не мой вызов.
2. Я провел тест с немногим более 27 тыс. строк, и для отображения предполагаемого плана выполнения требуется много времени, как вы думаете, могу ли я каким-либо образом оптимизировать код?
3. @Throkar Может быть, не пытайтесь обновлять 27 тысяч строк одновременно, используя любой подход? Я бы сказал, что 10 КБ за раз, вероятно, здесь приличная верхняя граница, может быть, даже меньше.
4. … и либо вам нужно обновить тысячи и тысячи строк, либо вы этого не делаете. если вы собираетесь выбрать подход, основанный на относительных оценочных планах выполнения, прекратите делать это, присоединившись к списку из 27 тыс. постоянных значений и поместите их в таблицу. Затем вы можете размещать ключи, добавлять индексы, извлекать выгоду из статистики и т. Д.
5. Ну, в основном, что я делаю, это использую программу, которую я создал, для копирования файлов с одного NAS на другой, и мне нужно обновить регистры, связанные с этими файлами в базе данных, и вставить новые регистры, которые имеют определенные требования, в другую базу данных, для этого я создаю сценарии в кодедля запуска отдельно, поэтому я попытался сделать этот скрипт для масштабного обновления всякий раз, когда я заканчиваю копирование файлов.
Ответ №2:
Добрый день, Трокар,
Предполагая, что я понял ваши потребности (в чем я не совсем уверен), и поскольку вы используете значения с жестким кодом (VALUES (1, 'Path 1'), (2, 'Path 2'))
, тогда, возможно, простое прямое обновление может решить ваши потребности
Поскольку вы не предоставили DDL DML, я буду использовать базовую демонстрацию
-- Let's assume that this our DDL DML
drop table if exists tableOperation
GO
CREATE TABLE tableOperation(IdRegister int, Path varchar(100))
INSERT tableOperation(IdRegister) values (2),(4),(5)
select * from tableOperation
GO
--UPDATE d
--SET Path = t.Path
--FROM dbo.tableOperation d
--JOIN (VALUES (1, 'Path 1'),(2, 'Path 2')) t (IdRegister, Path)
-- ON t.IdRegister = d.IdRegist
-- You can use this query
UPDATE dbo.tableOperation
SET Path = CASE
WHEN IdRegister = 1 then 'Path 1'
WHEN IdRegister = 2 then 'Path 2'
END
WHERE IdRegister in (1,2)
В фильтре (условие WHERE) Я использую жестко запрограммированный список всех значений, которые вы использовали в условии ON, а в разделе SET я просто использую оператор CASE с жестким кодом условий
Может ли этот подход удовлетворить ваши потребности?