обновление атрибутов записи в нескольких таблицах

#sql #tsql #ssis #for-loop #dynamic-sql

#sql #tsql #ssis #for-цикл #динамический-sql

Вопрос:

Мне нужно обновить вхождения select в разных таблицах атрибута [ISD_ID], как я могу это сделать?

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

 SELECT c1.TABLE_NAME FROM INFORMATION_SCHEMA.COLUMNS c1
INNER JOIN information_schema.COLUMNS c2
ON c1.TABLE_NAME = c2.TABLE_NAME
 WHERE c1.COLUMN_NAME LIKE '%isd%id%' and c2.column_name LIKE '%schooldistrict%id%'
  

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

Согласно предложению в другом сообщении, я прочитал о динамическом SQL. Итак, я мог бы сделать что-то вроде EXECUTE IMMEDIATE: ('update' @tablename ' set ISD_ID=37 where SchoolDistrictID=46') .

Тогда мой вопрос таков: как я могу выполнить итерацию по именам моих таблиц и подставить их в приведенную выше инструкцию в качестве @tablename переменной, чтобы я мог обновлять значения в каждой таблице?

У меня также есть возможность использовать .При необходимости используйте NET и SSIS.

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

Ответ №1:

  • Странный способ, которым вы можете использовать недокументированную хранимую процедуру (пожалуйста, не говорите Ремусу Русану, что я это сказал), чтобы сделать что-то вроде этого. Вы бы использовали условие @where, чтобы указать, что таблица должна содержать данный столбец.

  • Более традиционным способом было бы

    1. выберите результаты запроса во временную таблицу или табличную переменную
    2. выполните итерацию по временной таблице / табличной переменной, используя цикл while, беря имя таблицы и заменяя в переменной @tablename
    3. Выполните приведенный выше запрос. Внимание, вы, вероятно, захотите создать переменную с именем что-то вроде @myDynamicSQL, присвоить ей текст инструкции, а затем немедленно вызвать EXEC для нее.

Честно говоря, к тому времени, когда вы закончите с «странным способом», вам было бы лучше сделать это обычным способом, но я просто пытаюсь быть тщательным.

Комментарии:

1. Следуя вашему предложению, я получаю сообщение об ошибке, необходимо объявить скалярную переменную в строке set @tablename при выполнении: DECLARE @MyTable AS TABLE ( Table_nm NVARCHAR(128) NULL ) DECLARE @tablename AS NVARCHAR(128) DECLARE @myDynamicSQL AS TEXT = 'update' @tablename 'set ISD_ID=37 where SchoolDistrictID=46' WHILE ( SELECT Table_nm FROM @MyTable ) IS NOT NULL BEGIN SET @tablename = [HERE I GET ERROR -->]@MyTable.Table_nm EXECUTE IMMEDIATE @myDynamicSQL CONTINUE END GO

2. @SebastianVal—вы должны использовать Table_nm в переменной. Итак, сработало бы что-то вроде этого: SELECT TOP 1 @tablename=table_nm from @myTable . Теперь я бы также был осторожен и убедился, что вы либо удаляете запись из @mytable, когда закончите с ней, либо используете счетчик для предотвращения бесконечного цикла.

Ответ №2:

Если вы хотите использовать SSIS для этого, вы можете перенести результат вашего первого запроса в конечный набор записей.

Затем вы можете выполнить цикл foreach для переменной, которая хранит набор записей, а затем, например, создать SQL-задачу с выражением, которое выполняет вашу "UPDATE " (DT_STR,255,1252)@[User::tblname] " SET ....." функцию sqlStatementSource.

Комментарии:

1. (где User::tblname — это переменная, которая содержит текущее значение для вашего столбца набора записей, который является именем таблицы)

2. Спасибо за ваш ответ. Это кажется самым простым способом сделать это, но я собираюсь попробовать свои силы в изучении нового SQL.

3. Затем вы можете довольно легко выполнить это, наведя курсор на свой запрос, а затем динамически выполнить sql.