挖土

Coding for fun.
  博客园  :: 首页  :: 新随笔  :: 联系 :: 订阅 订阅  :: 管理

SQL 中的中位值计算

Posted on 2010-01-18 17:07  挖土.  阅读(1019)  评论(0编辑  收藏  举报
1. 在Northwind数据库上建立一个视图 VOrders

代码
SET NOCOUNT ON;
USE Northwind;
GO

IF OBJECT_ID('dbo.VOrders'IS NOT NULL
  
DROP VIEW dbo.VOrders;
GO
CREATE VIEW dbo.VOrders
AS

SELECT O.OrderID, O.OrderDate, O.CustomerID, O.EmployeeID, O.ShipVia,
  
SUM(OD.Quantity) AS Qty,
  
CAST(SUM(OD.Quantity * UnitPrice * (1 - Discount)) AS DECIMAL(122)) AS Value 
FROM dbo.Orders AS O
  
JOIN [Order Details] AS OD
    
ON O.OrderID = OD.OrderID
GROUP BY O.OrderID, O.OrderDate, O.CustomerID, O.EmployeeID, O.ShipVia
GO

 
2. 计算整个表中数据的中位值 (MSSQL 2000的做法)

代码
SELECT
(
 (
SELECT MAX(Value) FROM
   (
SELECT TOP 50 PERCENT Value FROM dbo.VOrders ORDER BY Value) AS H1)
 
+
 (
SELECT MIN(Value) FROM
   (
SELECT TOP 50 PERCENT Value FROM dbo.VOrders ORDER BY Value DESCAS H2)
/ 2 AS Median;

 


3. 用子查询来查询每个员工的中位值(MSSQL 2000的做法)

代码
SELECT EmployeeID,
(
 (
SELECT MAX(Value) FROM
   (
SELECT TOP 50 PERCENT Value FROM dbo.VOrders AS O1
    
WHERE O1.EmployeeID = E.EmployeeID
    
ORDER BY Value) AS H1)
 
+
 (
SELECT MIN(Value) FROM
   (
SELECT TOP 50 PERCENT Value FROM dbo.VOrders AS O2
    
WHERE O2.EmployeeID = E.EmployeeID
    
ORDER BY Value DESCAS H2)
/ 2 AS Median
FROM dbo.Employees AS E;

 


4.1 SQL 2005的做法,首先我们看看用来计算中位值的行的数据,这里用到了通用表(CTE)和Row_Number函数

代码
WITH OrdersRN AS
(
  
SELECT EmployeeID, Value,
    ROW_NUMBER() 
OVER(PARTITION BY EmployeeID ORDER BY Value) AS RowNum,
    
COUNT(*OVER(PARTITION BY EmployeeID) AS Cnt
  
FROM dbo.VOrders
)
SELECT EmployeeID, Value, RowNum, Cnt
FROM OrdersRN
WHERE RowNum IN((Cnt + 1/ 2, (Cnt + 2/ 2);

 


4.2 SQL 2005中,用通用表和Row_Number函数来计算中位值

 

代码
WITH OrdersRN AS
(
  
SELECT EmployeeID, Value,
    ROW_NUMBER() 
OVER(PARTITION BY EmployeeID ORDER BY Value) AS RowNum,
    
COUNT(*OVER(PARTITION BY EmployeeID) AS Cnt
  
FROM dbo.VOrders
)
SELECT EmployeeID, AVG(Value) AS Median
FROM OrdersRN
WHERE RowNum IN((Cnt + 1/ 2, (Cnt + 2/ 2)
GROUP BY EmployeeID;

 

 

关键词:中位值,中位值计算,Median,CTE,Row_Number