设置Rowcount影响嵌入式标量函数

时间:2013-05-25 16:06:50

标签: sql sql-server

我有一个SQL查询,其中嵌入了一个标量值函数。该函数从表中的各行中选择名称,并使用逗号作为分隔符将它们连接起来。对于例如ABC,DEF,XYZ。我为查询设置了ROWCOUNT只为1,因为我只想要1条记录。问题是如果我将ROWCOUNT设置为1,我的标量函数会产生意想不到的结果,即ABC而不是ABC,DEF,XYZ。

有人可以帮忙吗?我被限制只使用ROWCOUNT而不是TOP子句。

1 个答案:

答案 0 :(得分:0)

SET ROWCOUNT将影响外部SELECT语句和标量UDF中包含的任何SELECT语句的外层返回的行。

因此,除非您可以更改标量UDF的定义,否则无法单独使用SET ROWCOUNT

我假设您正在使用undocumented and un guaranteed变量分配方法。如果您更改为XML PATH方法,那么最顶层SELECT仅返回1行,它将不受SET ROWCOUNT 1命令的影响。

示例代码

    USE tempdb;
GO
    CREATE FUNCTION dbo.Concat1(@number INT = 0)
    RETURNS NVARCHAR(max)
    AS
      BEGIN
          DECLARE @Result NVARCHAR(max)

          SELECT @Result = COALESCE(@Result + ',','') + name
          FROM   master..spt_values
          WHERE  number = @number

          RETURN @Result
      END
GO
    CREATE FUNCTION dbo.Concat2(@number INT = 0)
    RETURNS NVARCHAR(max)
    AS
      BEGIN
          RETURN
            (SELECT STUFF((SELECT ',' + name AS [text()]
                           FROM   master..spt_values
                           WHERE  number = @number
                           FOR XML PATH('')), 1, 1, ''))
      END
GO
    SET ROWCOUNT 1;

    SELECT dbo.Concat1(number) AS Concat1,
           dbo.Concat2(number) AS Concat2
    FROM   master..spt_values
    WHERE  number = 1

    DROP FUNCTION dbo.Concat1, dbo.Concat2 

结果

+---------+--------------------------------------------------------------------------------------------------------------------------------------------------------------------+
| Concat1 |                                                                              Concat2                                                                               |
+---------+--------------------------------------------------------------------------------------------------------------------------------------------------------------------+
| rpc     | rpc,yes,autoclose,published,WINDOWS/NT,trusted,ignore duplicate keys,binary,varbinary,primary,NULL,Xact,NUL,GRANT,system table,disable_def_cnst_check,default disk |
+---------+--------------------------------------------------------------------------------------------------------------------------------------------------------------------+