Sql 根据经理id打印的最大sal
我有这张桌子:Sql 根据经理id打印的最大sal,sql,sql-server,Sql,Sql Server,我有这张桌子: id mgr_id sal 1 5 5000 2 5 6000 3 6 7000 4 6 8000 我预计这一产出: id mgr_id sal MaX_sal 1 5 5000 6000 2 5 6000 6000 3 6 7000 8000 4 6 8000 8000 根据mgr\u id选择max sal并在id前面打印 提前感谢。可能是sel
id mgr_id sal
1 5 5000
2 5 6000
3 6 7000
4 6 8000
我预计这一产出:
id mgr_id sal MaX_sal
1 5 5000 6000
2 5 6000 6000
3 6 7000 8000
4 6 8000 8000
根据mgr\u id
选择max sal并在id前面打印
提前感谢。可能是select中的子选择(尽管所有子选择都有点慢):
使用SQL Server 2012只需使用以下查询:
SELECT d.id, d.mgr_id, d.sal, MAX(sal) over(partition by mgr_id)
FROM @data d
您可以将此查询与SQL Server=2005一起使用:
SELECT d.id, d.mgr_id, d.sal, m.mx
FROM @data d
INNER JOIN (
SELECT mgr_id, mx = MAX(sal) FROM @data
GROUP BY mgr_id
) m
ON m.mgr_id = d.mgr_id;
SELECT d.id, d.mgr_id, d.sal, m.mx
FROM @data d
CROSS APPLY (SELECT mx = MAX(sal) FROM @data m WHERE m.mgr_id = d.mgr_id) m(mx)
Declare @data table([id] int, [mgr_id] int, [sal] int);
INSERT INTO @data([id], [mgr_id], [sal])
VALUES
(1, 5, 5000),
(2, 5, 6000),
(3, 6, 7000),
(4, 6, 8000)
;
样本数据:
SELECT d.id, d.mgr_id, d.sal, m.mx
FROM @data d
INNER JOIN (
SELECT mgr_id, mx = MAX(sal) FROM @data
GROUP BY mgr_id
) m
ON m.mgr_id = d.mgr_id;
SELECT d.id, d.mgr_id, d.sal, m.mx
FROM @data d
CROSS APPLY (SELECT mx = MAX(sal) FROM @data m WHERE m.mgr_id = d.mgr_id) m(mx)
Declare @data table([id] int, [mgr_id] int, [sal] int);
INSERT INTO @data([id], [mgr_id], [sal])
VALUES
(1, 5, 5000),
(2, 5, 6000),
(3, 6, 7000),
(4, 6, 8000)
;
这即使在SQLServer6.5中也可以工作
SELECT id, mgr_id, sal,
(
SELECT MAX(sal)
FROM employees mgr
WHERE mgr.mgr_id = emp.mgr_id
) AS max_sal
FROM
employees emp
这适用于SQL Server 2005:
WITH max_sals AS
(
SELECT mgr_id, MAX(sal) AS max_sal
FROM employees
GROUP BY mgr_id
)
SELECT emp.*, max_sals.max_sal
FROM
employees emp
LEFT JOIN max_sals
ON emp.mgr_id = max_sals.mgr_id
使用partiton:
SELECT emp.*, MAX(emp.sal) OVER (PARTITION BY emp.mgr_id) AS max_sal
FROM employees emp
样本数据和表格:
CREATE TABLE employees
(
id int,
mgr_id int,
sal int
)
INSERT INTO employees VALUES
(1,5,5000),
(2,5,6000),
(3,6,7000),
(4,6,8000)
按mrg_id创建子表分组,以获得每个mrg_id的最大Sal,然后将其与mrg_id上的主体表左键联接--尝试以下操作:
declare @table table (id int,mrg_id int,sal decimal(10,0))
insert into @table
select 1, 5, 5000 union all
select 2, 5, 6000 union all
select 3, 6, 7000 union all
select 4, 6, 8000
/***** change @table with your table name *****/
SELECT
t.id,
t.mrg_id,
t.sal,
t1.max_sal
FROM @table t
LEFT JOIN
(SELECT
mrg_id,
MAX(sal) max_sal
FROM @table
group by
mrg_id) t1
on t.mrg_id=t1.mrg_id
尝试交叉应用
SELECT id,
mgr_id,
sal,
Max_sal
FROM #your_table A
CROSS APPLY (SELECT Max(SAL) AS Max_sal
FROM #your_table B
WHERE B.mgr_id = A.mgr_id)cs
谢谢Diogo Rocha。请提供任何答案。请提供有关
Max\u sal
的更多详细信息。它是如何工作的?不应该是3、6、7000、8000?更新了输出。请立即检查此id的sal和基于mgr_id的分组,然后将max(sal)返回到所属id前面。出于兴趣(目前无法尝试)与分组逐子选择的内部连接与子选择的速度一样快(包括a)在我的虚拟机上的select?中有一个小表,没有索引、子select、内部连接、交叉应用会给出类似的结果。但不要想当然。它会随着表设计、数据、索引的不同而变化……为什么要使用左连接?@Julien Vavasseur LEFT-JOIN没有坏处。在SQL Server的某些版本中,内部联接会混淆基数估计。你对这个答案投了反对票吗?@Julien Vavasseur我使用左联接,因为我在子表中使用了相同的表,而且它的性能更好。没有理由否决这个答案!!!很抱歉,迟了回复@Amine Zaminex。我刚刚在2008年到2012年的测试中使用了样本表上的所有答案、随机值、ID上的PK w/o或索引(mgr_ID,sal desc)include(ID)或(mgr_ID)include(sal,ID),以及100、1000、10.000或100.000行和w/o或where(其中mgr_ID=X)。内部连接总是提供最好的性能和查询计划,尽管MAX-over有时要好一点。当有更多行时,W/o(左)变得更靠近或类似于内部。在Where中,无论行数多少,INNER始终优于LEFT。LEFT和CTE给出了相同的计划和性能。请参阅前面的评论@Jesús LópezYes!。6.5是我开发的第一个SQL Server版本。很久以前的名字了,但我希望不再需要了:)