SQL Server ДЛЯ КАЖДОЙ петли
У меня есть следующий SQL-запрос:
DECLARE @MyVar datetime = '1/1/2010'
SELECT @MyVar
Это, естественно, возвращает '1/1/2010'.
Что я хочу сделать, так это список дат, скажем:
1/1/2010
2/1/2010
3/1/2010
4/1/2010
5/1/2010
Затем я хочу ДЛЯ КАЖДОГО через числа и запустить SQL-запрос.
Что-то вроде (псевдокод):
List = 1/1/2010,2/1/2010,3/1/2010,4/1/2010,5/1/2010
For each x in List
do
DECLARE @MyVar datetime = x
SELECT @MyVar
Итак, это вернет: -
1/1/2010 2/1/2010 3/1/2010 4/1/2010 5/1/2010
Я хочу, чтобы это возвращало данные как один набор результатов, а не несколько наборов результатов, поэтому мне может понадобиться использовать какой-то союз в конце запроса, поэтому каждая итерация петлевого объединения на следующий.
изменить
У меня есть большой запрос, который принимает параметр "до даты", мне нужно запускать его 24 раза, каждый раз с конкретными датами, которые мне нужно предоставить (эти даты будут динамическими) я хотите избежать повторения моего запроса 24 раза с объединением всех, присоединяющихся к ним, как будто мне нужно вернуться и добавить дополнительные столбцы, это будет очень трудоемким.
Ответы
Ответ 1
SQL - это, прежде всего, ориентированный на набор язык язык - обычно это плохая идея использовать в нем цикл.
В этом случае аналогичный результат может быть достигнут с использованием рекурсивного CTE:
with cte as
(select 1 i union all
select i+1 i from cte where i < 5)
select dateadd(d, i-1, '2010-01-01') from cte
Ответ 2
Вот опция с переменной таблицы:
DECLARE @MyVar TABLE(Val DATETIME)
DECLARE @I INT, @StartDate DATETIME
SET @I = 1
SET @StartDate = '20100101'
WHILE @I <= 5
BEGIN
INSERT INTO @MyVar(Val)
VALUES(@StartDate)
SET @StartDate = DATEADD(DAY,1,@StartDate)
SET @I = @I + 1
END
SELECT *
FROM @MyVar
Вы можете сделать то же самое с временной таблицей:
CREATE TABLE #MyVar(Val DATETIME)
DECLARE @I INT, @StartDate DATETIME
SET @I = 1
SET @StartDate = '20100101'
WHILE @I <= 5
BEGIN
INSERT INTO #MyVar(Val)
VALUES(@StartDate)
SET @StartDate = DATEADD(DAY,1,@StartDate)
SET @I = @I + 1
END
SELECT *
FROM #MyVar
Вы должны сказать нам, какова ваша главная цель, как было сказано в @JohnFx, это, вероятно, может быть сделано другим (более эффективным) способом.
Ответ 3
Вы можете использовать таблицу переменных, например:
declare @num int
set @num = 1
declare @results table ( val int )
while (@num < 6)
begin
insert into @results ( val ) values ( @num )
set @num = @num + 1
end
select val from @results
Ответ 4
Этот вид зависит от того, что вы хотите делать с результатами. Если вы сразу же после цифр, параметр на основе набора будет таблицей чисел - это пригодится для всех видов вещей.
Для MSSQL 2005+ вы можете использовать рекурсивный CTE для создания строки чисел inline:
;WITH Numbers (N) AS (
SELECT 1 UNION ALL
SELECT 1 + N FROM Numbers WHERE N < 500
)
SELECT N FROM Numbers
OPTION (MAXRECURSION 500)
Ответ 5
declare @counter as int
set @counter = 0
declare @date as varchar(50)
set @date = cast([email protected] as varchar)+'/01/2013'
while(@counter < 12)
begin
select cast([email protected] as varchar)+'/01/2013' as date
set @counter = @counter + 1
end
Ответ 6
Конечно, старый вопрос. Но у меня есть простое решение, где нет необходимости в цикле, CTE, табличных переменных и т.д.
DECLARE @MyVar datetime = '1/1/2010'
SELECT @MyVar
SELECT DATEADD (DD,NUMBER,@MyVar)
FROM master.dbo.spt_values
WHERE TYPE='P' AND NUMBER BETWEEN 0 AND 4
ORDER BY NUMBER
Примечание: spt_values
является недокументированной таблицей Mircrosoft. У него есть номера для каждого типа. Его нельзя использовать, так как его можно удалить в любых новых версиях сервера SQL без предварительной информации, поскольку он не имеет документов. Но мы можем использовать его как быстрый обходной путь в некотором сценарии, как описано выше.
Ответ 7
[CREATE PROCEDURE [rat].[GetYear]
AS
BEGIN
-- variable for storing start date
Declare @StartYear as int
-- Variable for the End date
Declare @EndYear as int
-- Setting the value in strat Date
select @StartYear = Value from rat.Configuration where Name = 'REPORT_START_YEAR';
-- Setting the End date
select @EndYear = Value from rat.Configuration where Name = 'REPORT_END_YEAR';
-- Creating Tem table
with [Years] as
(
--Selecting the Year
select @StartYear [Year]
--doing Union
union all
-- doing the loop in Years table
select Year+1 Year from [Years] where Year < @EndYear
)
--Selecting the Year table
selec]