SQL - перебор записей таблицы - PullRequest
12 голосов
/ 05 февраля 2010

Я создал пользовательскую функцию, которая преобразует строку с разделителями-запятыми в таблицу. Я выполняю эту функцию так:

select [String] as 'ID' from dbo.ConvertStringToTable('1,2,3,4')

Результаты этого запроса выглядят следующим образом:

ID
--
1
2
3
4

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

Ответы [ 4 ]

13 голосов
/ 05 февраля 2010

В SQL SERVER 2000/05/08 вы можете использовать курсор, как показано ниже.

Однако, прежде чем идти по пути курсора, вы должны сначала изучить проблемы, связанные с курсорами в SQL Server.

DECLARE @id VARCHAR(10)

DECLARE myCursor CURSOR LOCAL FAST_FORWARD FOR
    SELECT [String] AS 'ID' 
    FROM [dbo].[ConvertStringToTable]('1,2,3,4')
OPEN myCursor
FETCH NEXT FROM myCursor INTO @id
WHILE @@FETCH_STATUS = 0 BEGIN
    PRINT @id
    -- do your tasks here

    FETCH NEXT FROM myCursor INTO @id

END

CLOSE myCursor
DEALLOCATE myCursor
5 голосов
/ 05 февраля 2010

Не используйте курсор, если вы можете избежать его, обычно все, что вам действительно нужно, это присоединиться к таблице, которую вы создали. Если ваш курсор выполняет обновление, вставку или удаление, у вас есть шанс 99,9%, что вам не нужен курсор. Курсоры должны быть техникой последнего курорта, а не первого курорта. Перебор записей почти всегда является плохим выбором в базе данных. Учись думать в сетах.

Почему вы должны избегать курсоров? Потому что они создают ночные кошмары. Я изменил процессы с 24 часов или больше до менее минуты, удалив curosr.

1 голос
/ 18 октября 2012

Используйте следующую функцию, которая принимает строку и символ разделителя ....

CREATE FUNCTION [dbo].[Udfsplitstring](@Text      VARCHAR(MAX), 
                                       @Delimiter VARCHAR(20) = ' ') 
-- @Strings table will contain values after separated by delimiter   
RETURNS @Strings TABLE ( 
  ID    INT IDENTITY PRIMARY KEY, 
  VALUE VARCHAR(MAX)) 
AS 
  BEGIN 
      DECLARE @Index INT 

      -- Set the index to -1 prior to run index through the loop   
      SET @Index = -1 

      -- Run loop till Text becomes empty   
      WHILE ( Len(@Text) > 0 ) 
        BEGIN 
            -- Getting the index of first delimiter   
            SET @Index = Charindex(@Delimiter, @Text) 

            -- Checking if there is no delimiter in Text   
            IF ( @Index = 0 ) 
               AND ( Len(@Text) > 0 ) 
              BEGIN 
                  -- Inserting text which separated by delimiter     
                  INSERT INTO @Strings 
                       VALUES (Rtrim(Ltrim(@Text))) 

                  BREAK 
              END 

            -- Checking if index found in Text then run the following script   
            IF ( @Index > 1 ) 
              BEGIN 
                  -- Inserting text after separated by delimiter     
                  INSERT INTO @Strings 
                       VALUES (LEFT(@Text, @Index - 1)) 

                  -- Separate the inserted value from text   
                  SET @Text = Rtrim(Ltrim(RIGHT(@Text, ( Len(@Text) - @Index ))) 
                              ) 
              END 
            ELSE 
              -- Separate the inserted value from text   
              SET @Text = Rtrim(Ltrim(RIGHT(@Text, ( Len(@Text) - @Index )))) 
        END 

      RETURN 
  END 
0 голосов
/ 05 февраля 2010

Ответом будут курсоры, но если есть шанс не использовать курсор, я бы предложил использовать другое решение.

Ваш запрос выглядит как запрос SQL Server, поэтому вот документация по SQL Server 2008.

http://msdn.microsoft.com/en-us/library/ms190028.aspx

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...