游标似乎只获取一条记录

时间:2013-04-10 22:24:49

标签: sql-server tsql stored-procedures cursor

我正在尝试这样做一个存储过程,对于每个Location =“Ubicacion”(计算固定asssets的数量= Ubicacion,总结这些资产的价值,并总结贬值的金额)当前放置在该位置的资产的那些资产。问题是光标似乎只提取一次

查询光标:

SELECT DISTINCT (ubicacion) FROM
         (SELECT activo, ubicacion, Fecha_Ubicacion, row_number() OVER (
            partition BY activo ORDER BY abs(datediff(dd, Fecha_Ubicacion, getdate()))
          ) AS RowNum FROM [SISACT].ACTIVO_UBICACION) someAlias WHERE RowNum = 1

结果:

Ubicacion
----------
1114
4450
4353

它应该取3次。 “位置”中的每条记录一个,以及位置中的最新记录。

    ALTER PROCEDURE [SISACT].[resume_activos]
AS
BEGIN
  DECLARE @u CHAR(8);
  DECLARE @p VARCHAR(8);
  DECLARE @num_activos INT = 0;
  DECLARE @monto_activos FLOAT = 0;
  DECLARE @saldo_dep_activos FLOAT = 0;

  DECLARE U CURSOR STATIC
    FOR SELECT DISTINCT (ubicacion) FROM
         (SELECT activo, ubicacion, Fecha_Ubicacion, row_number() OVER (
            partition BY activo ORDER BY abs(datediff(dd, Fecha_Ubicacion, getdate()))
          ) AS RowNum FROM [SISACT].ACTIVO_UBICACION) someAlias WHERE RowNum = 1
        OPEN U
    FETCH NEXT FROM U INTO @u
    WHILE @@FETCH_STATUS = 0
            BEGIN
        SELECT @num_activos = COUNT(a.Activo), @monto_activos = SUM(a.Costo_adquisicion), @saldo_dep_activos = SUM(a.Saldo_a_depreciar) FROM [SISACT].ACTIVOS_FIJOS a, [SISACT].UBICACIONES ub, (SELECT activo, ubicacion, Fecha_Ubicacion, row_number() OVER (
            partition BY activo ORDER BY abs(datediff(dd, Fecha_Ubicacion, getdate()))
          ) AS RowNum FROM [SISACT].ACTIVO_UBICACION) ab WHERE RowNum = 1 AND ub.Ubicacion = @u AND a.Activo = ab.Activo AND ab.Ubicacion = @u

           PRINT 'Ubicacion: ' +@u +' Num activos: ' + CONVERT(VARCHAR, @num_activos) + ' monto activos: ' + CONVERT(VARCHAR, @monto_activos) + ' saldo activos depreciados: '+ CONVERT(VARCHAR, @saldo_dep_activos)

                FETCH NEXT FROM U INTO @u
            END
    CLOSE U
    DEALLOCATE U

END

“打印”语句只在“消息”标签中显示一次,其中包含第一个位置和我前面所说的计算,再加上它没有返回任何内容,我希望它返回类似这样的内容

Ubicacion | Num_Act | Monto_Act | Saldo_dep_Act
------------------------------------------------
4453      |    2    | 5787.65   | 332.247

我是T-SQL的新手所以请原谅我,如果我做的事情非常愚蠢非常错,我之前只用光标做了一个SP并且它工作正常(它没有返回任何东西)。

我做错了什么?

提前谢谢。

1 个答案:

答案 0 :(得分:1)

它实际上正确地进行了计算。我更改了您的SP以在varchar(max)中累积输出并且仅在结尾处输出:

CREATE PROCEDURE [resume_activos]
AS
BEGIN
  DECLARE @u VARCHAR(8);
  DECLARE @p VARCHAR(8);
  DECLARE @allOutput VARCHAR(MAX) = '';
  DECLARE @num_activos INT = 0;
  DECLARE @monto_activos FLOAT = 0;
  DECLARE @saldo_dep_activos FLOAT = 0;

  DECLARE U CURSOR STATIC
    FOR SELECT DISTINCT (ubicacion) FROM
         (SELECT activo, ubicacion, Fecha_Ubicacion, row_number() OVER (
            partition BY activo ORDER BY abs(datediff(dd, Fecha_Ubicacion, getdate()))
          ) AS RowNum FROM ACTIVO_UBICACION) someAlias WHERE RowNum = 1
        OPEN U
    FETCH NEXT FROM U INTO @u
    WHILE @@FETCH_STATUS = 0
            BEGIN
        SELECT @num_activos = COUNT(a.Activo), @monto_activos = SUM(a.Costo_adquisicion), @saldo_dep_activos = SUM(a.Saldo_a_depreciar) FROM ACTIVOS_FIJOS a, UBICACIONES ub, (SELECT activo, ubicacion, Fecha_Ubicacion, row_number() OVER (
            partition BY activo ORDER BY abs(datediff(dd, Fecha_Ubicacion, getdate()))
          ) AS RowNum FROM ACTIVO_UBICACION) ab WHERE RowNum = 1 AND ub.Ubicacion = @u AND a.Activo = ab.Activo AND ab.Ubicacion = @u

           SET @allOutput = @allOutput + char(10) + char(13) + 'Ubicacion: ' +@u +' Num activos: ' + CONVERT(VARCHAR, @num_activos) + ' monto activos: ' + CONVERT(VARCHAR, @monto_activos) + ' saldo activos depreciados: '+ CONVERT(VARCHAR, @saldo_dep_activos)

                FETCH NEXT FROM U INTO @u
            END
    CLOSE U
    DEALLOCATE U
  SELECT @allOutput

END

输出是:

Ubicacion: 1114 Num activos: 2 monto activos: 2781.15 saldo activos depreciados: 53.1104
Ubicacion: 4450 Num activos: 1 monto activos: 4553 saldo activos depreciados: 126.472
Ubicacion: 4453 Num activos: 2 monto activos: 5787.65 saldo activos depreciados: 332.247

您可以在此处看到它:http://sqlfiddle.com/#!3/bce40/1/0

如果您希望将结果作为实际表,只需创建临时表,并在每次迭代时插入部分结果。然后在最后,从中选择以获得完整的结果集。