SQL Server 中的 FORWARD_ONLY 光标

SQL Server 中的 FORWARD_ONLY 光标不支持滚动。此 SQL FORWARD_ONLY 光标只能从第一行移动到最后一行,不支持反向滚动。这意味着 SQL FORWARD_ONLY 光标支持 FETCH_ONLY 选项,而对于所有其他 FETCH 选项都会返回错误。

SQL Server 允许我们将 STATIC、DYNAMIC 或 KEYSET 关键字与 FORWARD_ONLY 光标一起使用。如果您省略了这些关键字中的任何一个,SQL Server 将假定其为 DYNAMIC。

在此 SQL Server 中的 forward_only 光标演示中,我们使用下面显示的表。如您所见,我们的 Employee 表包含 14 条记录。

FORWARD_ONLY Cursor in SQL Server 1

SQL Server 中的 Forward_Only 光标示例 1

在此示例中,我们将向您展示如何在 SQL Server 中声明和打开一个 forward_only 光标。在这里,我们将使用不同的 FETCH 选项来演示支持的 fetch 选项。

DECLARE forward_employee_cursor CURSOR FORWARD_ONLY
    FOR SELECT * FROM [EmployeeTable]
OPEN forward_employee_cursor  
FETCH NEXT FROM forward_employee_cursor;

分析

下面的语句将声明名为 forward_employee_cursor 的 forward_only 光标,用于 Employee 表中的所有记录。

DECLARE forward_employee_cursor CURSOR FORWARD_ONLY
    FOR SELECT * FROM [EmployeeTable]

下面的语句将打开声明的光标。

OPEN forward_employee_cursor

下一条语句将从 forward_employee_cursor 光标中获取或返回下一条记录。

FETCH NEXT FROM forward_employee_cursor;

尽管我们的 employee 表有 14 条记录,但光标只检索了一条记录。这是因为 SQL Server 的 FETCH NEXT 只会从光标中获取一行,如果您想要全部获取,则需要使用循环。

FORWARD_ONLY Cursor in SQL Server 2

我来使用 FETCH FIRST 选项。如您所见,这会引发错误。

FORWARD_ONLY Cursor in SQL Server 3

我来使用 FETCH LAST 选项。

FORWARD_ONLY Cursor in SQL Server 4

接下来,我们使用了 FETCH PRIOR 选项。

FORWARD_ONLY Cursor in SQL Server 5

SQL Server 中的 Forward_Only 光标示例 2

让我们看看如何创建 FORWARD_ONLY STATIC 光标和 FORWARD_ONLY DYNAMIC 光标。为此,我们使用 DECLARE CURSOR 语句,并在其中使用 WHILE LOOP 来遍历光标元素并执行更新。

SET NOCOUNT ON
-- Declaring the Variables 
DECLARE @EmpID INT,
        @EmpName VARCHAR(50),
        @EmpEducation VARCHAR(50),
	@EmpOccupation VARCHAR(50),
	@EmpYearlyIncome DECIMAL (10, 2), 
	@EmpSales DECIMAL (10, 2);

DECLARE forward_employee_cursor CURSOR 
FORWARD_ONLY STATIC FOR 
	SELECT [ID]
	      ,[Name]
	      ,[Education]
	      ,[Occupation]
	      ,[YearlyIncome]
	      ,[Sales]
	FROM EmployeeTable
        ORDER BY Occupation

OPEN forward_employee_cursor
IF @@CURSOR_ROWS > 0
BEGIN 
      FETCH NEXT FROM forward_employee_cursor
            INTO @EmpID, @EmpName, @EmpEducation,
	         @EmpOccupation, @EmpYearlyIncome, @EmpSales
      WHILE @@FETCH_STATUS = 0
      BEGIN
	IF @EmpOccupation = N'Management'
 	    UPDATE [EmployeeTable] 
		SET [YearlyIncome] = 999999,
		    [Sales] = 15000
	    WHERE CURRENT OF forward_employee_cursor                
		
        FETCH NEXT FROM forward_employee_cursor
             INTO @EmpID, @EmpName, @EmpEducation,
	          @EmpOccupation, @EmpYearlyIncome, @EmpSales
      END
END
CLOSE forward_employee_cursor
DEALLOCATE forward_employee_cursor
SET NOCOUNT OFF 
GO

如果您观察光标声明,我们正在使用 SQL FORWARD_ONLY STATIC 光标,并执行 UPDATE 选项。我们在之前的文章中已经解释了其余步骤。我建议您参考 SQL Server 中的动态光标 和 Keyset 光标示例。

FORWARD_ONLY Cursor in SQL Server 6

您可以看到错误表明:该光标是只读的。这是因为我们在光标声明中提到了 FORWARD_ONLY STATIC。而 STATIC 光标 不支持 INSERT、DELETE 或 UPDATE 操作。

请使用以下 SQL 查询来检查光标是否已在 Employee 表中更新记录。

SELECT [ID]
      ,[Name]
      ,[Education]
      ,[Occupation]
      ,[YearlyIncome]
      ,[Sales]
  FROM [EmployeeTable]
FORWARD_ONLY Cursor in SQL Server 7

我将通过编写:FORWARD_ONLY DYNAMIC 来将光标声明从 static 更改为 dynamic。请记住,即使您忘记了 DYNAMIC 关键字,它也会起作用,因为它是 forward_only 触发器的默认关键字。

FORWARD_ONLY Cursor in SQL Server 8

现在您可以看到更新后的记录。

FORWARD_ONLY Cursor in SQL Server 9