嵌套Group BY Sql Query

时间:2014-04-24 09:11:41

标签: sql-server

我在我的sql server db中有以下三个表

1 - >群组列表

GroupID || GroupName 

2 - > MachineList

MachineID   || GroupID  || MachineName

3 - > CaptureLogs

LogID   || MachineID    || VoilationWord

我需要一个查询来获取以下报告

GroupName   || MachineCountInGroup  || TotalLogCountByMachinesInGroup

伙计们,请帮帮我。

4 个答案:

答案 0 :(得分:0)

你可以

  select GroupName ,
    (select count(1) from  MachineList where GroupID = grp.GroupID ) as    
     MachineCountInGroup   ,
   (select count(1) from  MachineList 
   inner join  CaptureLogs 
   on  CaptureLogs.MachineID=MachineList .MachineID   
   where GroupID  = grp.GroupID ) as TotalLogCountByMachinesInGroup
   from  GroupList grp

我确信有更好的方法,但这会有效。

答案 1 :(得分:0)

如果没有数据,很难肯定地说,但我猜这样的事情可能就是你所追求的?

SELECT DISTINCT gl.groupid , gl.groupname, COUNT(ml.MachineId) OVER (PARTITION BY gl.groupid) AS MachineCountInGroup, COUNT(cl.LogId) OVER (PARTITION BY cl.MachineId) AS TotalLogCOuntBYMachinesInGroup FROM dbo.GroupList AS gl JOIN dbo.MachineList AS ml ON ml.groupid = gl.groupid JOIN dbo.CaptureLogs AS cl ON cl.machineid = ml.MachineId

这会给出一些看似如下的数据: groupname, machinecountingroup, totallogcount... A 3 1 A 3 2 B 2 2

如果您只需要一行A,则需要调整

COUNT(cl.LogId) OVER (PARTITION BY cl.MachineId) AS TotalLogCOuntBYMachinesInGroup

类似

COUNT(cl.logid) OVER (PARTITION BY gl.groupid) AS TotalLogCOuntBYMachinesInGroup

这只会给你一行A和一行B. A 3 3 B 2 2 因此,我不知道你究竟在追求什么,这是我能做的最好的事情(再次 - 测试数据会很好)

答案 2 :(得分:0)

我准备了完整的脚本,然后是满足要求的最佳解决方案。

创建表格的脚本

create table GroupList
(GroupId int primary key, GroupName varchar(50) not null);

create table MachineList
(MachineId int primary key,
 GroupId int not null,
 MachineName varchar(50) not null
);

Alter table MachineList
Add foreign key(GroupId)
references GroupList(GroupId)

Create table CaptureLogs
(LogId int identity(1,1) primary key,
 MachineId int not null,
 VoilationWord varchar(50) not null
);

Alter table CaptureLogs
Add foreign key(MachineId)
references MachineList(MachineId);

现在脚本在表中插入一些示例数据:

Insert into GroupList Values(1,'Group 1'),(2,'Group 2');

Insert into MachineList 
values(1,1,'Machine 1'),(2,1,'Machine 2 of 1'),(3,2,'Machine 3 of 2'),(4,2,'Machine 4 of 2'),(5,2,'Machine 5 of 2');

Insert into CaptureLogs
    (MachineId, VoilationWord)
select MachineId, 'First Word from ' + MachineName from MachineList
union all
select MachineId, 'Second Word from ' + MachineName from MachineList
    where MachineId > 1
union all
select MachineId, 'Third Word from ' + MachineName from MachineList
    where MachineId > 2
union all
select MachineId, 'Fourth Word from ' + MachineName from MachineList
    where MachineId > 3
union all
select MachineId, 'Fifth Word from ' + MachineName from MachineList
    where MachineId > 4;

现在要获取所需的数据,您需要运行简单的代码。我认为这是最好的。

Select gl.GroupName, count(distinct ml.MachineId) MachineCountInGroup, 
        count(LogId) TotalLogCountByMachinesInGroup from GroupList gl
        inner join MachineList ml on gl.GroupId = ml.GroupId
        inner join CaptureLogs cl on ml.MachineId = cl.MachineId
        group by gl.GroupName;

我希望它有所帮助。

答案 3 :(得分:-1)

这将有效:

选择   g.GroupName,   COUNT(DISTINCT l.MachineID)AS MachineCountInGroup,   COUNT(*)AS TotalLogCountByMachinesInGroup 来自CaptureLogs l JOIN MachineList m ON m.MachineID = l.MachineID JOIN GroupList g ON g.GroupID = m.GroupID GROUP BY g.GroupName

顺便说一句,我希望计算l.MachineID为引擎提供更好的机会来优化访问,而不是计算m.MachineID。无论如何,2都是相同的,因为有一个INNER JOIN。

SQLFiddle上测试,因为我没有安装自己的SQL Server。