Pregunta

¿Hay algún método para aplicar bucle do while en el servidor SQL 2008?

¿Fue útil?

Solución

No estoy seguro acerca de do-while EN MS SQL Server 2008 pero se puede cambiar la lógica de bucle while, con el fin de utilizar como bucle do-while.

ejemplos están tomados de aquí: http://blog.sqlauthority.com/2007/10/24/sql-server-simple-example-of-while-loop-with-continue-and-break-keywords /

  1. Ejemplo de bucle while

    DECLARE @intFlag INT
    SET @intFlag = 1
    WHILE (@intFlag <=5)
    BEGIN
        PRINT @intFlag
        SET @intFlag = @intFlag + 1
    END
    GO
    

    conjunto de resultados:

    1
    2
    3
    4
    5
    
  2. Ejemplo de bucle while con rotura de la palabra clave

    DECLARE @intFlag INT
    SET @intFlag = 1
    WHILE (@intFlag <=5)
    BEGIN
        PRINT @intFlag
        SET @intFlag = @intFlag + 1
        IF @intFlag = 4
            BREAK;
    END
    GO
    

    conjunto de resultados:

    1
    2
    3
    
  3. Ejemplo de bucle while con CONTINUAR y rotura Palabras clave

    DECLARE @intFlag INT
    SET @intFlag = 1
    WHILE (@intFlag <=5)
    BEGIN
        PRINT @intFlag
        SET @intFlag = @intFlag + 1
        CONTINUE;
        IF @intFlag = 4 -- This will never executed
            BREAK;
    END
    GO
    

    conjunto de resultados:

    1
    2
    3
    4
    5
    

Pero trata de bucles Evita a nivel de base de datos. Referencia .

Otros consejos

Si no está muy ofendido por la palabra clave GOTO, que puede ser utilizado para simular un DO / WHILE en T-SQL. Considere el siguiente ejemplo bastante sin sentido escrito en pseudocódigo:

SET I=1
DO
 PRINT I
 SET I=I+1
WHILE I<=10

Este es el código T-SQL equivalente usando Ir a:

DECLARE @I INT=1;
START:                -- DO
  PRINT @I;
  SET @I+=1;
IF @I<=10 GOTO START; -- WHILE @I<=10

Aviso el que uno entre el GOTO solución y el pseudocódigo DO / WHILE original de activar. Una aplicación similar utilizando un bucle WHILE se vería así:

DECLARE @I INT=1;
WHILE (1=1)              -- DO
 BEGIN
  PRINT @I;
  SET @I+=1;
  IF NOT (@I<=10) BREAK; -- WHILE @I<=10
 END

Ahora, usted podría, por supuesto, volver a escribir este ejemplo en particular como un simple bucle WHILE, ya que este no es un candidato tan bueno para una construcción DO / WHILE. Se hizo hincapié en ejemplo brevedad en lugar de aplicabilidad, ya que los casos legítimos que requieren un DO / WHILE son raros.


REPEAT / hasta que, cualquier persona (no funciona en T-SQL)?

SET I=1
REPEAT
  PRINT I
  SET I=I+1
UNTIL I>10

... y la solución basada en GOTO T-SQL:

DECLARE @I INT=1;
START:                    -- REPEAT
  PRINT @I;
  SET @I+=1;
IF NOT(@I>10) GOTO START; -- UNTIL @I>10

A través del uso creativo de GOTO y la inversión de la lógica a través de la palabra clave NOT, existe una relación muy estrecha entre el pseudocódigo original y la solución basada GOTO. Una solución similar utilizando un aspecto de bucle WHILE como:

DECLARE @I INT=1;
WHILE (1=1)       -- REPEAT
 BEGIN
  PRINT @I;
  SET @I+=1;
  IF @I>10 BREAK; -- UNTIL @I>10
 END

Un argumento puede ser hecho de que para el caso de la REPEAT / UNTIL, la solución basada WHILE es más simple, debido a que la si la condición no se invierte. Por otro lado, también se mostrará más información.

Si no fuera por todo el desdén en torno al uso de GOTO, estos podrían incluso ser soluciones idiomáticas para esos pocos momentos en los que estas en particular (mal) construcciones de bucle son necesarios en el código T-SQL en aras de la claridad.

Uso éstos a su propia discreción, tratando de no sufrir la ira de sus compañeros desarrolladores cuando te pillan usando la tan denostada GOTO.

Me parece recordar de leer este artículo más de una vez, y la respuesta es solamente cerrar para lo que necesito.

Por lo general, cuando pienso que voy a necesitar un DO WHILE en T-SQL que es porque estoy iteración de un cursor, y estoy buscando en gran medida para una óptima claridad (frente a la velocidad óptima). En T-SQL que parece encajar un WHILE TRUE / IF BREAK.

Si ese es el escenario que le trajo aquí, este fragmento puede ahorrar un momento. De lo contrario, la bienvenida de nuevo, yo. Ahora puedo tener la certeza de que he estado aquí más de una vez. :)

DECLARE Id INT, @Title VARCHAR(50)
DECLARE Iterator CURSOR FORWARD_ONLY FOR
SELECT Id, Title FROM dbo.SourceTable
OPEN Iterator
WHILE 1=1 BEGIN
    FETCH NEXT FROM @InputTable INTO @Id, @Title
    IF @@FETCH_STATUS < 0 BREAK
    PRINT 'Do something with ' + @Title
END
CLOSE Iterator
DEALLOCATE Iterator

Por desgracia, T-SQL no parece ofrecer una forma más limpia de forma individual a definir el funcionamiento de ciclo, que este bucle infinito.

También puede utilizar una variable de salida si desea que su código sea un poco más fácil de leer:

DECLARE @Flag int = 0
DECLARE @Done bit = 0

WHILE @Done = 0 BEGIN
    SET @Flag = @Flag + 1
    PRINT @Flag
    IF @Flag >= 5 SET @Done = 1
END

Esto probablemente sería más relevante cuando se completa un ciclo más complicada y está tratando de hacer un seguimiento de la lógica. Como bucles indicados son caros, así que tratar de utilizar otros métodos si es posible.

Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top