SQL 服务器 - 嵌套 While 循环中的全局变量重置

SQL Server - Global Variable Resets in Nested While Loop

我有一个全局变量,它在嵌套 While 循环中递增。在每次迭代中,它将值重置为 1(即初始初始化值)。

示例可重现代码:

SET NOCOUNT ON;
DECLARE @GlobalCounter INT = 1;
DECLARE @CounterOne INT = 1;
DECLARE @CounterTwo INT = 1;

WHILE(@CounterOne <= 10)
BEGIN
    PRINT 'Outer Loop:';
    PRINT @GlobalCounter;

    DECLARE @SerialInfo table
    (
        [Id] [int] IDENTITY(1,1) NOT NULL,
        [SNumber] [NVARCHAR](20) NOT NULL,
        PRIMARY KEY ([Id])
    );

    SET @CounterTwo = 1;
    WHILE(@CounterTwo <= 10)
    BEGIN

        DECLARE @SerialNumber NVARCHAR(20);
        SET @SerialNumber = 'SRL: ' + CONVERT(NVARCHAR(10), @GlobalCounter);

        INSERT INTO @SerialInfo([SNumber]) VALUES (@SerialNumber);

        SET @GlobalCounter = @GlobalCounter + 1;
        SET @CounterTwo = @CounterTwo + 1;
    END

    SET @CounterTwo = 1;
    WHILE(@CounterTwo <= 10)
    BEGIN
        SET @SerialNumber = '';
        SELECT @SerialNumber = [SNumber] FROM @SerialInfo WHERE [Id] = @CounterTwo;
        PRINT @SerialNumber;
        SET @CounterTwo = @CounterTwo + 1;
    END

    SET @CounterOne = @CounterOne + 1;
END

请在全局变量作用域及其值方面帮助我。如何实现预期结果

SRL: 1
SRL: 2
SRL: 3
.
.
.
SRL: 99
SRL: 100

Resultant Image

问题在于您提供的查询,您只查询前 10 [SNumber]

WHILE(@CounterTwo <= 10)
BEGIN
    SET @SerialNumber = '';
    SELECT @SerialNumber = [SNumber] FROM @SerialInfo WHERE [Id] = @CounterTwo;

检查该查询是否符合您的业务逻辑:

SET NOCOUNT ON;
DECLARE @GlobalCounter = 1;
DECLARE @CounterOne INT = 1;
DECLARE @CounterTwo INT = 1;

WHILE(@CounterOne <= 10)
BEGIN
    DECLARE @SerialInfo table
    (
        [Id] [int] IDENTITY(1,1) NOT NULL,
        [SNumber] [NVARCHAR](20) NOT NULL,
        PRIMARY KEY ([Id])
    );

    SET @CounterTwo = 1;
    WHILE(@CounterTwo <= 10)
    BEGIN

        DECLARE @SerialNumber NVARCHAR(20);
        SET @SerialNumber = 'SRL: ' + cast(@globalCounter as varchar)

        INSERT INTO @SerialInfo([SNumber]) VALUES (@SerialNumber);
        SET @GlobalCounter = @GlobalCounter + 1;
        SET @CounterTwo = @CounterTwo + 1;
    END
    SET @CounterOne = @CounterOne + 1;
END
set @CounterTwo = 1
WHILE(@CounterTwo <= @GlobalCounter)
BEGIN
    SET @SerialNumber = '';
    SELECT @SerialNumber = [SNumber] FROM @SerialInfo WHERE [Id] = @CounterTwo;
    PRINT @SerialNumber;
    SET @CounterTwo = @CounterTwo + 1;
END

在 T-SQL 中,变量声明参与控制流。因此,仅仅因为 declare @SerialInfo table... 出现在循环内,并不意味着 @SerialInfo 每次通过循环时都会 重新初始化 作为一个空的 table。

一旦在解析每个批次时遇到变量声明,变量名就会从那时起生效,直到批次结束。

例如这有效:

if 1=0
begin
    declare @a int
end
set @a = 15
print @a

不幸的是,您当前的代码是如此程序化,以至于很难看出您试图完成和制作的实际任务修复它的建议。但它可能不需要循环并依赖生成的 IDENTITY 值。


希望从上面可以清楚地看到您所看到的 - @SerialInfo 最终包含 100 行,其中包含您显然想要的所有值。但是由于您的 print 循环仅查询 table 的前 10 行,它继续输出与外循环 运行.[=16 第一次插入的相同的 10 行=]