选择的第一个孩子记录在TSQL
问题描述:
一个selfjoin我有一个visits
表看起来像这样:选择的第一个孩子记录在TSQL
id identity(1,1) not null,
visit_date datetime not null,
patient_id int not null,
flag bit not null
对于每一个记录,我需要找到一个匹配的记录是同时或更早,具有相同的patient_id,并具有flag
设置为1。我现在正在做的是:
select parent.id as parent_id,
(
select top 1
child.id as child_id
from
visits as child
where
child.visit_date <= parent.visit_date
and child.patient_id = parent.patient_id
and child.flag = 1
order by
visit_date desc
) as child_id
from
visits as parent
所以,此查询工作正常,但它运行太慢了 - 我怀疑这是因为子查询。是否有可能将其重写为联接查询?
答
/*
id identity(1,1) not null,
visit_date datetime not null,
patient_id int not null,
flag bit not null
*/
SELECT
T.parentId,
T.patientId,
V.id AS childId
FROM
(
SELECT
visit.id AS parentId,
visit.patient_id AS patientId,
MAX (previous_visit.visit_date) previousVisitDate
FROM
visit
LEFT JOIN visit previousVisit ON
visit.patient_id = previousVisit.patient_id
AND visit.visit_date >= previousVisit.visit_date
AND visit.id <> previousVisit.id
AND previousVisit.flag = 1
GROUP BY
visit.id,
visit.visit_date,
visit.patient_id,
visit.flag
) AS T
LEFT JOIN visit V ON
T.patientId = V.patient_id
AND T.previousVisitDate = V.visit_date
答
查看查询执行计划。如果你有粗箭头,看看这些陈述。你应该学习不同的语句以及它们暗示的内容,比如聚簇索引扫描/寻找等。
通常当查询进行得很慢时,我发现没有好的索引。
受影响并用于连接的表和列,创建一个涵盖所有这些列的索引。这通常在论坛中被称为覆盖指数。这是你可以为真正需要的东西做的事情。但请记住,太多索引会减慢插入语句的速度。