我有一张桌子:[tblEmp]
EmpId | EmpName | DeptId
和表[tblSalary]
EmpId | Salary
我需要找到在其部门中拥有最高薪水的员工名单。
我可以通过以下方式实现这一目标:
SELECT *
FROM tblEmp
JOIN tblSal ON tblSal.EmpId = tblEmp.EmpId
WHERE LTRIM(STR(deptid)) + LTRIM(STR(salary)) IN (
SELECT LTRIM(STR(deptid)) + LTRIM(STR(MAX(salary)))
FROM tblSal
JOIN tblEmp ON tblSal.EmpId = tblEmp.EmpId
GROUP BY DeptId
)
有没有更好的方法来实现清单?
答案 0 :(得分:5)
您可以尝试使用ROW_NUMBER。
返回结果分区中行的序号 设置,从1开始,每个分区的第一行。
像
这样的东西;WITH Employees AS (
SELECT e.*,
ROW_NUMBER() OVER(PARTITION BY e.DeptId ORDER BY s.salary DESC) RowID
FROM [tblEmp] e INNER JOIN
[tblSalary] s ON e.EmpId = s.EmpId
)
SELECT *
FROM Employees
WHERE RowID = 1
但是,这不会返回同一部门中具有相同salry的员工。
为此,您可能需要查看RANK (Transact-SQL)或DENSE_RANK (Transact-SQL)而不是ROW_NUMBER。
等级:返回结果集分区中每行的等级。该 行的等级是一行加上行之前的等级数 问题。
如果两个或更多行绑定排名,则每个绑定的行都会收到相同的排 秩。
Dense_Rank :返回结果分区中的行级别 设置,排名没有任何差距。一行的等级是一加 排在相关行之前的不同排名的数量。
答案 1 :(得分:2)
这通常是您使用分析函数的地方:
SELECT *
FROM ( SELECT tblSal.*, tblEmp.*,
RANK() OVER (PARTITION BY tblEmp.deptid ORDER BY tblSal.salary DESC) as SalaryRank
FROM tblEmp
JOIN tblSal ON tblSal.EmpId = tblEmp.EmpId
)
WHERE SalaryRank = 1