是否可以创建通用 SP 来确定中位数?
Is it possible to create a generic SP to determine Median?
我正在使用 SQL Server 2012。我想我想问的是我是否应该继续研究创建 SP(或 UDF,但可能涉及#Temp 表,我正在考虑 SP) 以便有一个可重用的对象来确定中位数?
我希望这不是一个太笼统的问题,而且很简单,但我花了一些时间研究确定中值的能力。一些可能的障碍包括需要传递查询的字符串表示形式,该查询将 return 我希望对其执行中值的数据。
过去有人尝试过吗?
如果使用 SQL Server 2008 或更新版本(您是),您可以编写一个接受 table-valued parameter
作为输入的函数。
Create Type MedianData As Table ( DataPoint Int )
Create Function CalculateMedian ( @MedianData MedianData ReadOnly )
Returns Int
As
Begin
-- do something with @MedianData which is a table
End
这是我用来生成一些快速统计数据的存储过程。
只需传递源、测量 and/or 过滤器。
CREATE PROCEDURE [dbo].[prc-Dynamic-Stats](@Table varchar(150),@Fld varchar(50), @Filter varchar(500))
-- Syntax: Exec [dbo].[prc-Dynamic-Stats] '[Chinrus-Series].[dbo].[DS_Treasury_Rates]','TR_Y10','Year(TR_Date)>2001'
As
Begin
Set NoCount On;
Declare @SQL varchar(max) =
'
;with cteBase as (
Select RowNr=Row_Number() over (Order By ['+@Fld+'])
,Measure = ['+@Fld+']
From '+@Table+'
Where '+case when @Filter='' then '1=1' else @Filter end+'
)
Select RecordCount = Count(*)
,DistinctCount = Count(Distinct A.Measure)
,SumTotal = Sum(A.Measure)
,Minimum = Min(A.Measure)
,Maximum = Max(A.Measure)
,Mean = Avg(A.Measure)
,Median = Max(B.Measure)
,Mode = Max(C.Measure)
,StdDev = STDEV(A.Measure)
From cteBase A
Join (Select Measure From cteBase where RowNr=(Select Cnt=count(*) from cteBase)/2) B on 1=1
Join (Select Top 1 Measure,Hits=count(*) From cteBase Group By Measure Order by 2 desc ) C on 1=1
'
Exec(@SQL)
End
Returns
RecordCount DistinctCount SumTotal Minimum Maximum Mean Median Mode StdDev
3615 391 12311.81 0.00 5.44 3.4057 3.57 4.38 1.06400795277565
您可能想看一下我必须 post 的回复。简而言之,如果您熟悉 C# 或 VB .NET,则可以创建用户定义的 CLR 聚合。我们将 CLR 实现用于很多事情,尤其是您可能在其他平台(如 SAS、R 等)中看到的统计方法
这可以通过 SQLCLR 创建用户定义的聚合 (UDA) 轻松实现。如果您想了解如何操作,甚至只是下载 UDA,请查看我在 SQL Server Central 上写的关于它的文章:Getting The Most Out of SQL Server 2005 UDTs and UDAs(请注意,该站点需要免费注册才能阅读他们的内容)。
或者,它也可以在 SQL# SQLCLR 库(我创建的,但它是免费的)的免费版本中提供,可在 http://SQLsharp.com/ 获得。它被称为Agg_Median.
我正在使用 SQL Server 2012。我想我想问的是我是否应该继续研究创建 SP(或 UDF,但可能涉及#Temp 表,我正在考虑 SP) 以便有一个可重用的对象来确定中位数?
我希望这不是一个太笼统的问题,而且很简单,但我花了一些时间研究确定中值的能力。一些可能的障碍包括需要传递查询的字符串表示形式,该查询将 return 我希望对其执行中值的数据。
过去有人尝试过吗?
如果使用 SQL Server 2008 或更新版本(您是),您可以编写一个接受 table-valued parameter
作为输入的函数。
Create Type MedianData As Table ( DataPoint Int )
Create Function CalculateMedian ( @MedianData MedianData ReadOnly )
Returns Int
As
Begin
-- do something with @MedianData which is a table
End
这是我用来生成一些快速统计数据的存储过程。
只需传递源、测量 and/or 过滤器。
CREATE PROCEDURE [dbo].[prc-Dynamic-Stats](@Table varchar(150),@Fld varchar(50), @Filter varchar(500))
-- Syntax: Exec [dbo].[prc-Dynamic-Stats] '[Chinrus-Series].[dbo].[DS_Treasury_Rates]','TR_Y10','Year(TR_Date)>2001'
As
Begin
Set NoCount On;
Declare @SQL varchar(max) =
'
;with cteBase as (
Select RowNr=Row_Number() over (Order By ['+@Fld+'])
,Measure = ['+@Fld+']
From '+@Table+'
Where '+case when @Filter='' then '1=1' else @Filter end+'
)
Select RecordCount = Count(*)
,DistinctCount = Count(Distinct A.Measure)
,SumTotal = Sum(A.Measure)
,Minimum = Min(A.Measure)
,Maximum = Max(A.Measure)
,Mean = Avg(A.Measure)
,Median = Max(B.Measure)
,Mode = Max(C.Measure)
,StdDev = STDEV(A.Measure)
From cteBase A
Join (Select Measure From cteBase where RowNr=(Select Cnt=count(*) from cteBase)/2) B on 1=1
Join (Select Top 1 Measure,Hits=count(*) From cteBase Group By Measure Order by 2 desc ) C on 1=1
'
Exec(@SQL)
End
Returns
RecordCount DistinctCount SumTotal Minimum Maximum Mean Median Mode StdDev
3615 391 12311.81 0.00 5.44 3.4057 3.57 4.38 1.06400795277565
您可能想看一下我必须
这可以通过 SQLCLR 创建用户定义的聚合 (UDA) 轻松实现。如果您想了解如何操作,甚至只是下载 UDA,请查看我在 SQL Server Central 上写的关于它的文章:Getting The Most Out of SQL Server 2005 UDTs and UDAs(请注意,该站点需要免费注册才能阅读他们的内容)。
或者,它也可以在 SQL# SQLCLR 库(我创建的,但它是免费的)的免费版本中提供,可在 http://SQLsharp.com/ 获得。它被称为Agg_Median.