使用sql中的查询在一行中显示多行?

使用sql中的查询在一行中显示多行?,sql,sql-server,Sql,Sql Server,我想在一行中显示EMP表中的部门号和每个部门的员工人数。我有一个查询,它将结果显示在单独的行中 select deptno, count(*) from emp group by deptno; Dptno Count(*) 10 5 20 3 30 4 我想将结果显示为一行。例如: Dpt10 Count(*) Dpt20 Count(*) Dpt30 Count(*) 10 5 20 3 30 4

我想在一行中显示EMP表中的部门号和每个部门的员工人数。我有一个查询,它将结果显示在单独的行中

select deptno, count(*) from emp
group by deptno;

Dptno Count(*)
10       5
20       3
30       4
我想将结果显示为一行。例如:

Dpt10 Count(*) Dpt20 Count(*) Dpt30 Count(*)
10      5        20     3       30     4
此论坛中的输出不正确,但请尝试理解5、3和4号应位于count*列下方,10、20和30号应位于deptno下方。

您可以尝试以下操作-

模式

质疑

输出

105203304


由于pivot不支持SQL Server中的多个聚合:

with t as (
select 10 id, 15 su union all
select 10 id, 10 su  union all
select 10 id, 5 su  union all
select 20 id, 135 su  union all
select 20 id, 100 su  union all
select 20 id, 15 su  union all
select 30 id, 150 su  union all
select 30 id, 1000 su  union all
select 30 id, 500 su 
)
select max(case when id = 10 then id end) dept10
     , count(case when id = 10 then id end) dept10_cnt
     , max(case when id = 20 then id end) dept20
     , count(case when id = 20 then id end) dept20_cnt
     , max(case when id = 30 then id end) dept30
     , count(case when id = 30 then id end) dept30_cnt
  from t

在SQL Server中,有几种方法可以将多行数据转换为列

如果只需要将每个deptno的计数转换为列,那么可以使用PIVOT函数或CASE/aggregate组合轻松地完成这项工作

select 
  sum(case when deptno = 10 then 1 else 0 end) Count_Dpt10,
  sum(case when deptno = 20 then 1 else 0 end) Count_Dpt20,
  sum(case when deptno = 30 then 1 else 0 end) DCount_pt30
from emp

但问题的一部分是,您希望将DeptNo和Total_计数都集中到列中—这需要使用两个不同的聚合函数。在您的情况下,PIVOT函数不起作用,因此您必须使用不同的聚合函数以及类似于以下内容的CASE表达式:

select 
  max(case when deptno = 10 then deptno end) Dpt10,
  sum(case when deptno = 10 then 1 else 0 end) Count_Dpt10,
  max(case when deptno = 20 then deptno end) Dpt20,
  sum(case when deptno = 20 then 1 else 0 end) Count_Dpt20,
  max(case when deptno = 30 then deptno end) Dpt30,
  sum(case when deptno = 30 then 1 else 0 end) DCount_pt30
from emp;
看。现在,由于您有未知的部门,所以需要使用动态sql。这将创建一个sql字符串,然后执行该字符串。要创建sql字符串,需要使用STUFF和FOR XML PATH。动态代码是:

DECLARE @cols AS NVARCHAR(MAX),
    @query  AS NVARCHAR(MAX)

select @cols 
  = STUFF((SELECT 
             ', max(case when deptno = '+cast(deptno as varchar(10))+' then deptno end) as '+ QUOTENAME('Dpt'+cast(deptno as varchar(10))) 
             + ', sum(case when deptno = '+cast(deptno as varchar(10))+' then 1 else 0 end) as '+ QUOTENAME('Count_Dpt'+cast(deptno as varchar(10))) 
            from emp
            group by deptno
            order by deptno
            FOR XML PATH(''), TYPE
            ).value('.', 'NVARCHAR(MAX)') 
        ,1,1,'')

set @query 
      = 'SELECT ' + @cols + ' 
         from emp'

exec sp_executesql @query;
看。这将为您提供一个结果:

| DPT10 | COUNT_DPT10 | DPT20 | COUNT_DPT20 | DPT30 | COUNT_DPT30 |
|-------|-------------|-------|-------------|-------|-------------|
|    10 |           5 |    20 |           3 |    30 |           4 |

标题重要吗?您可以返回一个串联字符串/10 20 30 5 3 4这是您要找的吗?10 5 20 3 30 4这是我想要的。@SumonBanerjee:检查我的答案…@SumonBanerjee-这是stuff的语法-stuff我们可以用动态方式来实现吗???如果列数@zaratura更多,则在max条件下添加列是不正确的。该解决方案不支持动态方式。如果需要所有id值,则需要指定所有id值。如果您熟悉Pivot子句,Pivot会使用聚合函数和其中的大小写重写查询。因此,如果我们必须处理更多列,则无法在select语句中继续增加列。如果我们需要处理Pivot,则可以使用dynamic way@Zaratutrayes,但结果将是xml。OP没有说任何他需要的动态方式。我根据OP提供的信息编写了这个查询。
DECLARE @cols AS NVARCHAR(MAX),
    @query  AS NVARCHAR(MAX)

select @cols 
  = STUFF((SELECT 
             ', max(case when deptno = '+cast(deptno as varchar(10))+' then deptno end) as '+ QUOTENAME('Dpt'+cast(deptno as varchar(10))) 
             + ', sum(case when deptno = '+cast(deptno as varchar(10))+' then 1 else 0 end) as '+ QUOTENAME('Count_Dpt'+cast(deptno as varchar(10))) 
            from emp
            group by deptno
            order by deptno
            FOR XML PATH(''), TYPE
            ).value('.', 'NVARCHAR(MAX)') 
        ,1,1,'')

set @query 
      = 'SELECT ' + @cols + ' 
         from emp'

exec sp_executesql @query;
| DPT10 | COUNT_DPT10 | DPT20 | COUNT_DPT20 | DPT30 | COUNT_DPT30 |
|-------|-------------|-------|-------------|-------|-------------|
|    10 |           5 |    20 |           3 |    30 |           4 |