1

我正在尝试为语句LEFT JOIN的每一行获取 a 的第一个结果。SELECT

因为现在,如果我在连接表中有 100 行,我将从SELECT. 我只需要第一个加入的行,这样我就不会得到任何重复。

我不能使用GROUP BY,因为我必须从表中获取不止一行。

这是我的查询的基本版本:

SELECT bg.PatientID, DATEDIFF(hour, bg.CreateDate, GETDATE()) TimeToTarget 
FROM BloodGlucose bg
    LEFT JOIN IVProtocol i ON i.PatientID = bg.PatientID
WHERE bg.BGValue >= i.TargetLow AND bg.BGValue <= i.TargetHigh
ORDER BY bg.PatientID ASC

我尝试使用DISTINCT,但由于来自的数据bg.CreateDate并不总是相同,它返回重复项。

我只需要左连接表的第一行。

有什么想法/建议吗?

谢谢!

4

2 回答 2

4
;WITH x AS 
(
  SELECT 
    bg.PatientID, 
    TimeToTarget = DATEDIFF(hour, bg.CreateDate, GETDATE()),
    rn = ROW_NUMBER() OVER (PARTITION BY bg.PatientID ORDER BY bg.CreatedDate DESC) 
  FROM dbo.BloodGlucose AS bg
  LEFT JOIN dbo.IVProtocol AS i 
  ON i.PatientID = bg.PatientID
  WHERE bg.BGValue >= i.TargetLow 
  AND bg.BGValue <= i.TargetHigh
)
SELECT PatientID, TimeToTarget
FROM x
WHERE rn = 1
ORDER BY PatientID;

加入其他结果:

;WITH x AS 
(
  ... same as above ...
)
SELECT x.PatientID, x.TimeToTarget, y.Something
 FROM x INNER JOIN dbo.SomethingElse AS y
 ON x.PatientID = y.PatientID
 WHERE x.rn = 1
 ORDER BY x.PatientID;
于 2012-08-13T17:20:37.100 回答
2
SELECT bg.PatientID, DATEDIFF(hour, bg.CreateDate, GETDATE()) TimeToTarget 
FROM BloodGlucose bg
cross apply (
 select top 1 *
 from IVProtocol i
 where i.PatientID = bg.PatientID
 order by SOME_CRITERA
) i
WHERE bg.BGValue >= i.TargetLow AND bg.BGValue <= i.TargetHigh
ORDER BY bg.PatientID ASC

对于这种情况,交叉应用是一个方便的工具。它的工作方式类似于连接,但您可以在子查询中使用变量。

于 2012-08-13T17:18:08.857 回答