У меня есть пара таблиц с ограничениями первичного ключа, которые я заполняю из C#.Самый быстрый способ вставки строк без нарушения первичного ключа
Каким будет самый быстрый способ вставки строк без нарушения первичного ключа?
Выполняет ли выполнение заявлений один за другим против партии, добавляет значительные накладные расходы?
Если мне нужно будет обновить определенные строки на основе условий, могу ли я лучше использовать хранимую процедуру и называть ее точками или использовать слияние?
1.
foreach(var point in points)
{
...
sqlCommand.ExecuteNonQuery(@"
BEGIN TRY
INSERT INTO POINTS ...
END TRY
BEGIN CATCH
IF ERROR_NUMBER() <> 2627
BEGIN
THROW
END
END CATCH", con)
}
2.
foreach(var point in points)
{
...
sqlCommand.ExecuteNonQuery(@"
IF NOT EXISTS (Select 1 from POINTS where ...)
INSERT INTO POINTS ...", con)
}
3.
StringBuilder sb = new StringBuilder();
sb.AppendLine("BEGIN TRAN");
foreach(var point in points)
{
sb.AppendLine("IF NOT EXISTS (Select 1 from POINTS where ...) INSERT INTO POINTS ...")
}
sb.AppendLine("COMMIT TRAN");
sqlCommand.ExecuteNonQuery(sb.ToString());
4.
StringBuilder sb = new StringBuilder();
sb.AppendLine(@"
BEGIN TRAN
DECLARE @POINTS TABLE (
...
)
");
foreach(var point in points)
{
sb.AppendLine("INSERT INTO @POINTS ...")
}
sb.AppendLine(@"
MERGE POINTS as T
USING @POINTS as S
ON T.KEY=S.KEY
WHEN OT MATCHED THEN
INSERT ...
");
sb.AppendLine("COMMIT TRAN");
sqlCommand.ExecuteNonQuery(sb.ToString());
Это самый эффективный способ. Просто вставьте его в таблицу хранения в базе данных, затем вы можете использовать все команды на основе SQL, чтобы массировать данные в ваши живые таблицы. – dbugger
Таким образом, объединение между #NEW_POINTS и таблицей POINTS будет работать лучше, чем с переменной @POINTS? Я думал, что из-за того, что слияние является одним из фильтрующих строк, производительность вставки внутри временного значения ничтожно мала. – adrianvlupu
Я бы ожидал, что MERGE выполнит то же самое, независимо от того, использует ли таблица temp #POINTS или переменную @POINTS. Однако использование SqlBulkCopy почти наверняка будет быстрее, чем НАСЫЩЕНИЕ точек отдельно (foreach (точка в точках в точках) ...). – Max