Member 14800672 Ответов: 1

Как выполнить цикл через инструкцию select и передать определенное поле каждого возвращаемого значения из select в хранимую процедуру


Итак, предположим, что мой оператор select возвращает следующее

Id   Name
--   ----
1    Name1
2    Name2
3    Name3


и у меня есть хранимая процедура (называемая doLogic), которая берет идентификатор и выполняет некоторую логику

то, что я хочу сделать, - это передать каждый идентификатор, возвращенный из инструкции select, в хранимую процедуру, поэтому я подумал, что должен сделать цикл, но не знал, как это сделать. я читал кое-что о курсоре, но не мог этого сделать.

Что я уже пробовал:

поэтому в основном я выбираю свой стол

выберите *из таблицы
я должен сделать петлю здесь
{
таблица exec doLogic.Id - и передайте каждый tableId внутрь
}

Gerry Schmitz

Что вы планируете делать с результатами / кодами возврата? Откуда берутся эти "множественные" запросы? Знаете ли вы, что такое DDOS-атака?

1 Ответов

Рейтинг:
10

CHill60

SQL-это язык, основанный на множествах. Очень и очень редко вам нужно использовать петлю.
Рассмотрите возможность изменения хранимой процедуры для получения требуемых данных путем присоединения к ней table вместо.

Если "некоторая логика" не пытается обновить таблицу, просто верните значение, а затем создайте функцию и вызовите ее как часть select, например

select [Id], [name], MyFunction([name]) as Result from [table]
Некоторое время назад я написал статью об альтернативах циклам, но она также включает в себя некоторые примеры циклов, если вам абсолютно необходимо использовать один из них - см. Циклы обработки в SQL Server[^]

Редактировать после комментария OP
---------------------
Цитата:
что делает моя хранимая процедура
это вставка в две таблицы с использованием одного и того же идентификатора и удаление из 2 других таблиц с использованием одного и того же идентификатора

create procedure doLogic
@Id int

Insert into table1(Id) values @Id
Insert into table2(Id) values @Id

delete from table3 where Id = @Id
delete from table4 where Id = @Id

Return 0


Вот некоторые примеры данных, которые соответствуют таблицам, которые вы использовали в своих примерах
create table #table (id int identity(1,1), [name] varchar(50))
insert into #table ([name]) values
('name A'),('name B'),('name C'),('name D')

create table #table1 (id int)	
create table #table2 (id int)   

create table #table3 (id int)
insert into #table3 (id) values (3),(7) 

create table #table4 (id int)
insert into #table4 (id) values (1),(4),(8),(9) 
Используя этот пример данных, в хранимой процедуре я мог бы заменить
Insert into table1(Id) values @Id
Insert into table2(Id) values @Id
это делает вставку один за другим (или RBAR = строка за мучительной строкой - не помню, кто это говорит. Я посмотрю его позже), с двумя строками, которые будут делать всю таблицу сразу т.е.
insert into #table1 select [id] from #table 
insert into #table2 select [id] from #table
Я могу использовать несколько альтернативных идей для замены
delete from table3 where Id = @Id
delete from table4 where Id = @Id
Первый из них тривиален и просто удаляет все, что соответствует ...
delete from #table3 where [id] in (select id from #table)
Этот второй по сути точно такой же, но я включил его, чтобы попытаться показать, что вы можете сделать подзапрос таким сложным, как вам нравится
delete from #table4 where [id] in (select #table4.id from #table inner join #table4 on #table.id = #table4.id)

Вы также упоминали
Цитата:
и можете ли вы объяснить пример функции, который вы упомянули больше? как заменить его на select, который возвращает все записи? что мне нужно передать в хранимую процедуру?
Пользовательская функция не может изменять записи, она может возвращать только значения, поэтому теперь, когда я знаю, что вы пытаетесь сделать в своей хранимой процедуре, это неуместно. Оставь это на другой раз


Member 14800672

Привет Остынь,

что делает моя хранимая процедура
это вставка в две таблицы с использованием одного и того же идентификатора и удаление из 2 других таблиц с использованием одного и того же идентификатора

создать процедуру doLogic
@Id int

Вставить в таблицу 1(Id) значения @Id
Вставить в таблицу 2(Id) значения @Id

удалить из табл. 3, где Id = @Id
удалить из табл. 4, где Id = @Id

Возвращает 0


вот почему я думал, что должен сделать цикл и вставить каждый идентификатор, как вы думаете, что лучше всего сделать в моем случае?

и можете ли вы объяснить пример функции, который вы упомянули больше? как заменить его на select, который возвращает все записи? что мне нужно передать в хранимую процедуру?

CHill60

Я обновил свое решение

Member 14800672

Большое спасибо Chill60, это было очень полезно, не могли бы вы взглянуть на это?
это как-то похоже
https://www.codeproject.com/Questions/5275815/How-to-insert-more-than-one-record-in-a-new-table

CHill60

Я был недостаточно быстр! :) Ричард уже опубликовал решение для вас