我可以为聚合函数对数据进行排序吗?

Can I sort data for an aggregate function?

我有一个自定义的 CLR 聚合函数。此函数连接组内的字符串。现在的问题是,我可以让这个函数以某种特定的顺序处理数据,还是它始终是数据库找到的某种随机顺序 suitable?我知道对于大多数数学聚合函数(MIN、MAX、AVG 等)来说,处理数据的顺序没有区别,但是假设我想在一个组中按字母顺序连接字符串,我可以做些什么来实现这一点结果?

请注意,它必须是一个聚合函数(不要被下面的例子误导)并且改变现有的 CLR 函数是不可行的问题(它所做的只是一个基本的字符串连接,仅此而已).

我测试了将 ORDER BY 添加到包含 GROUP BYSELECT,但没有产生任何有意义的结果。

SELECT
    user.Id, dbo.concat(cat.Name)
FROM
    Users user
    JOIN Cats cat ON (cat.Owner = user.Id)
GROUP BY user.Id
ORDER BY user.Id, MAX(cat.Name) --kind of meaningless really

我还尝试 ORDER BY table 包含我想在执行 JOIN 之前连接的数据,但结果是一样的。

SELECT
    user.Id, dbo.concat(cat.Name)
FROM
    Users user
    JOIN (SELECT TOP 100 PERCENT /*hack*/ c.* FROM Cats c ORDER BY c.Name) cat ON (cat.Owner = user.Id)
GROUP BY user.Id

在子查询中排序数据然后执行 GROUP BY 也没有用。

SELECT
    t1.Id, dbo.concat(t1.Name)
FROM
(
    SELECT TOP 100 PERCENT /*hack*/
        user.Id, cat.Name
    FROM
        Users user
        JOIN Cats cat ON (cat.Owner = user.Id)
    ORDER BY user.Id, cat.Name
) t1
GROUP BY t1.Id

我本来以为这些都行不通,但至少现在没有人可以说我什么都没试过。

P.S。是的,我有理由不使用FOR XML PATH。如果无法完成我在这里提出的要求,我将接受它。

您可以在 order by 子句中包含函数。

用这个虚拟日期返回器试试:

create function testDate ()
returns datetime
as
begin
    declare @returnDate datetime
    select @returnDate = CURRENT_TIMESTAMP

    return @returnDate
end

运行 带有任何 table 的函数(用真实的 table 替换 SomeTable)并按它排序:

select  dbo.testDate (),
        *
from    SomeTable
order by dbo.testDate () desc

@jahu 编辑:我以为你想通过用户定义的函数来订购。也许我误解了这个问题。您可以通过这样的聚合函数对查询进行排序:

select  CustomerID,
        avg(OrderID)
from    Orders
group by CustomerID 
order by avg(OrderID) desc

上面的table将OrderID作为一个唯一的列,并且可以有多个CustomerID记录

根据来自 Damien_The_Unbeliever、Vladimir Baranov、Microsoft 页面和少数其他用户的信息(参见问题的评论),我可以推断:

  • 无法直接在数据库中为聚合函数排序行;然而,有迹象表明此 is\might 是计划中的功能(请参阅 here and here);如果 MS 实现了这一点,一些现有的 CLR 聚合函数可能会开始表现得很奇怪(因为默认情况下这些聚合函数被标记为依赖于顺序)
  • 必须直接在 CLR 函数中实现排序;这可能有点棘手due to how CLR aggregate functions are being run,但可以做到

不幸的是,我没有一段代码可以在这里展示,因为我没有时间更改我的 CLR 函数(并且在我的情况下进行无序连接就足够了)。