如何基于PK列加入4个表?

时间:2014-09-01 15:19:23

标签: sql sql-server tsql sql-server-2008-r2

在我的存储过程中,我有四个选择查询。这些查询中共有一列JobDescriptionCode。我想在该列上加入这些表。

这是我的存储过程:

SELECT a.JobDescriptionCode, ISNULL(a.ApprovedCount,0) -  ISNULL(b.ApprovedCount,0) AS StructureChange
FROM
(select rh.JobDescriptionCode, SUM(ApprovedCount) as ApprovedCount from RequisitionHistory rh 
left join OGJobDescription jd on rh.JobDescriptionCode = jd.JobDescriptionCode
where Convert(varchar(8),rh.CreationDate,1) between @PreviousMonthStartDate and @PreviousMonthEndDate
GROUP by rh.JobDescriptionCode) a
INNER JOIN
(select rh.JobDescriptionCode, SUM(ApprovedCount) as ApprovedCount from RequisitionHistory rh 
left join OGJobDescription jd on rh.JobDescriptionCode = jd.JobDescriptionCode
where Convert(varchar(8),rh.CreationDate,1) between @startDate and @endDate
GROUP by rh.JobDescriptionCode) b
on a.JobDescriptionCode = b.JobDescriptionCode

select r.JobDescriptionCode, count(*) as NewJoining from CandidateHistory ch 
left join Requisition r on ch.RequisitionCode = r.RequisitionCode
where ch.StatusCode = 6005 and Convert(varchar(8),ch.CreationDate,1) between @startDate and @endDate
GROUP BY r.JobDescriptionCode

select r.JobDescriptionCode, count(*) as Separation from CandidateHistory ch 
left join Requisition r on ch.RequisitionCode = r.RequisitionCode
where ch.StatusCode = 10005 and Convert(varchar(8),ch.CreationDate,1) between @startDate and @endDate
GROUP BY r.JobDescriptionCode

SELECT r.JobDescriptionCode, d.DepartmentName,jd.JobDescriptionName, SUM(r.ApprovedCount) as ApprovedCount, SUM(r.FilledCount) as FilledCount,
SUM(r.UnfilledCount) as UnfilledCount  from Requisition r
left join OGJobDescription jd on r.JobDescriptionCode = jd.JobDescriptionCode
left join OGDepartment d on r.DepartmentCode = d.DepartmentCode
where Convert(varchar(8),r.RequisitionDate,1) between @startDate and @endDate
GROUP BY jd.JobDescriptionName, d.DepartmentName, r.JobDescriptionCode

现在,日期作为参数传递给SP,基于1个月。现在一些查询返回2行,大约10行,依此类推。我只想匹配PK JobDescriptionCode,然后加入表格。

是否有可能,如果是这样的话?

2 个答案:

答案 0 :(得分:2)

您可以将每个单独的查询视为子查询,并将它们连接在一起,如下所示:

SELECT q1.JobDescriptionCode, StructureChange, NewJoining, Separation, DepartmentName, JobDescriptionName, ApprovedCOUNT, FilledCOUNT, UnfilledCOUNT  
FROM (
    SELECT 
        a.JobDescriptionCode, 
        ISNULL(a.ApprovedCOUNT,0) - ISNULL(b.ApprovedCOUNT,0) AS StructureChange
    FROM (
        SELECT rh.JobDescriptionCode, SUM(ApprovedCOUNT) AS ApprovedCOUNT 
        FROM RequisitionHistory rh 
        LEFT JOIN OGJobDescription jd ON rh.JobDescriptionCode = jd.JobDescriptionCode
        WHERE CONVERT(VARCHAR(8),rh.CreationDate,1) BETWEEN @PreviousMonthStartDate AND @PreviousMonthEndDate
        GROUP BY rh.JobDescriptionCode
    ) a
    INNER JOIN (
        SELECT rh.JobDescriptionCode, SUM(ApprovedCOUNT) AS ApprovedCOUNT 
        FROM RequisitionHistory rh 
        LEFT JOIN OGJobDescription jd ON rh.JobDescriptionCode = jd.JobDescriptionCode
        WHERE CONVERT(VARCHAR(8),rh.CreationDate,1) BETWEEN @startDate AND @endDate
        GROUP BY rh.JobDescriptionCode
    ) b ON a.JobDescriptionCode = b.JobDescriptionCode
) q1

INNER JOIN (
    SELECT r.JobDescriptionCode, COUNT(*) AS NewJoining 
    FROM CANDidateHistory ch 
    LEFT JOIN Requisition r ON ch.RequisitionCode = r.RequisitionCode
    WHERE ch.StatusCode = 6005 AND CONVERT(VARCHAR(8),ch.CreationDate,1) BETWEEN @startDate AND @endDate
    GROUP BY r.JobDescriptionCode
) q2 ON q1.JobDescriptionCode = q2.JobDescriptionCode

INNER JOIN (
    SELECT r.JobDescriptionCode, COUNT(*) AS Separation 
    FROM CANDidateHistory ch 
    LEFT JOIN Requisition r ON ch.RequisitionCode = r.RequisitionCode
    WHERE ch.StatusCode = 10005 AND CONVERT(VARCHAR(8),ch.CreationDate,1) BETWEEN @startDate AND @endDate
    GROUP BY r.JobDescriptionCode
) q3 ON q1.JobDescriptionCode = q3.JobDescriptionCode

INNER JOIN (
    SELECT 
        r.JobDescriptionCode, 
        d.DepartmentName,
        jd.JobDescriptionName, 
        SUM(r.ApprovedCOUNT) AS ApprovedCOUNT, 
        SUM(r.FilledCOUNT) AS FilledCOUNT, 
        SUM(r.UnfilledCOUNT) AS UnfilledCOUNT  
    FROM Requisition r
    LEFT JOIN OGJobDescription jd ON r.JobDescriptionCode = jd.JobDescriptionCode
    LEFT JOIN OGDepartment d ON r.DepartmentCode = d.DepartmentCode
    WHERE CONVERT(VARCHAR(8),r.RequisitionDate,1) BETWEEN @startDate AND @endDate
    GROUP BY jd.JobDescriptionName, d.DepartmentName, r.JobDescriptionCode
) q4 ON q1.JobDescriptionCode = q4.JobDescriptionCode

在仔细查看您的查询后,我认为可以简化一下,看起来会多一些。

编辑:我认为这个查询应该是等价的,但没有测试数据就有点难以确认。如果它产生正确的输出,它可能表现更好:

SELECT 
    q1.JobDescriptionCode, 
    q1.StructureChange, 
    q2.NewJoining, 
    q2.Separation, 
    q3.DepartmentName, 
    q3.JobDescriptionName, 
    q3.ApprovedCount, 
    q3.FilledCount, 
    q3.UnFilledCount  
FROM (
    SELECT rh.JobDescriptionCode, 
        SUM(CASE 
            WHEN CONVERT(VARCHAR(8),rh.CreationDate,1) BETWEEN @startDate AND @endDate THEN -ApprovedCount 
            WHEN CONVERT(VARCHAR(8),rh.CreationDate,1) BETWEEN @PreviousMonthStartDate AND @PreviousMonthEndDate THEN ApprovedCount
        END) AS StructureChange 
    FROM RequisitionHistory rh 
    LEFT JOIN OGJobDescription jd ON rh.JobDescriptionCode = jd.JobDescriptionCode      
    GROUP BY rh.JobDescriptionCode
) q1
INNER JOIN (
    SELECT 
        r.JobDescriptionCode, 
        SUM(CASE WHEN ch.StatusCode = 6005 THEN 1 ELSE 0 END) AS NewJoining,
        SUM(CASE WHEN ch.StatusCode = 10005 THEN 1 ELSE 0 END) AS Separation 
    FROM CandidateHistory ch 
    LEFT JOIN Requisition r ON ch.RequisitionCode = r.RequisitionCode
    WHERE CONVERT(VARCHAR(8),ch.CreationDate,1) BETWEEN @startDate AND @endDate
    GROUP BY r.JobDescriptionCode
) q2 ON q1.JobDescriptionCode = q2.JobDescriptionCode
INNER JOIN (
    SELECT 
        r.JobDescriptionCode, 
        d.DepartmentName,
        jd.JobDescriptionName, 
        SUM(r.ApprovedCount) AS ApprovedCount, 
        SUM(r.FilledCount) AS FilledCount, 
        SUM(r.UnFilledCount) AS UnFilledCount  
    FROM Requisition r
    LEFT JOIN OGJobDescription jd ON r.JobDescriptionCode = jd.JobDescriptionCode
    LEFT JOIN OGDepartment d ON r.DepartmentCode = d.DepartmentCode
    WHERE CONVERT(VARCHAR(8),r.RequisitionDate,1) BETWEEN @startDate AND @endDate
    GROUP BY jd.JobDescriptionName, d.DepartmentName, r.JobDescriptionCode
) q3 ON q1.JobDescriptionCode = q3.JobDescriptionCode

答案 1 :(得分:2)

尝试将所有查询都放入WITH中,如下所示:

WITH table_alias1 AS (
SELECT ...
),
table_alias2 AS (
SELECT .. ),
table_alias3 AS (
SELECT .. ),
table_alias4 AS (
SELECT .. )
SELECT * FROM 
 table_alias1 t1 INNER JOIN
 table_alias2 t2 ON t1.JobDescriptionCode = t2.JobDescriptionCode INNER JOIN
 table_alias2 t3 ON t1.JobDescriptionCode = t3.JobDescriptionCode INNER JOIN
 table_alias2 t4 ON t1.JobDescriptionCode = t4.JobDescriptionCode;

您的查询量很大,因此出于可读性原因,我没有把它们放在这里。