解释:
您需要查找在给定日期访问过同一专业的两位不同医生的患者列表。
在此要求中,您的Patient
表成为主表。让我们先查询该表。
现在我们有了患者名单。我们需要得到他们访问过的医生的名单。我们不能简单地将患者表与医生表连接起来,因为没有用于映射数据的列。我们必须使用 Visits 作为中间表
LEFT OUTER JOIN
在 Patient 和 Visits 表之间添加一个并按pid列加入。
我们有病人和他们就诊的名单,但现在我们需要获取医生的信息。LEFT OUTER JOIN
因此,在 Visits 和 Doctors 表之间添加另一个,并通过did列加入。
我们有患者和医生就诊信息。但是,我们只需要患者的姓名、就诊医生的专业和就诊日期。因此,我们将在SELECT子句和GROUP BY子句中添加列p.pname
和。除此之外,我们需要所有访问次数,但有一个问题。我们只需要 DISTINCT 计数,换句话说,我们需要他们访问过的所有唯一医生的计数。因此,如果患者在一天内两次拜访同一位医生,则应计为 1。因此,在这里添加将有所帮助。此外,关键是使用正确的列名,在这种情况下d.did代表医生。d.speciality
v.date
DISTINCT
我们拥有我们需要的所有数据,但我们只需要过滤在同一天拜访了两位不同医生的患者。为此,HAVING 子句可以帮助我们。当您应用 GROUP BY 时,HAVING 是合适的。我们将使用相同的 COUNT(DISTINCT d.did) 来检查计数是否仅与2的值匹配。您可以在输出中看到结果。
建议:
您不必为插入到表中的每个值指定 INSERT INTO 语句。您可以在括号内将它们组合在一起,并用 . 分隔它们commas
。最后一条语句应以semicolon
.
该查询使用LEFT OUTER JOIN
. 我使用此联接来找出每位患者的所有就诊次数,即使他们从未看过医生。我只是想在形成查询时查看输出。您可以将其更改为INNER JOIN
,我认为这更适合您的场景。
如果您不想显示访问次数,可以将其从 SELECT 子句中删除。
演示:
单击此处查看 SQL Fiddle 中的演示。
解释中使用的脚本:
SELECT p.pname
, d.speciality
, v.date
, COUNT(DISTINCT d.did) AS visitcount
FROM Patient p
LEFT OUTER JOIN Visits v
ON v.pid = p.pid
LEFT OUTER JOIN Doctors d
ON d.did = v.did
GROUP BY p.pname
, d.speciality
, v.date
HAVING COUNT(DISTINCT d.did) = 2
更适合您的脚本:
SELECT p.pname
, d.speciality
, v.date
FROM Patient p
INNER JOIN Visits v
ON v.pid = p.pid
INNER JOIN Doctors d
ON d.did = v.did
GROUP BY p.pname
, d.speciality
, v.date
HAVING COUNT(DISTINCT d.did) = 2
输出:
PNAME SPECIALITY DATE VISITCOUNT
--------- ------------ --------- -----------
Loch Ness Assholes 17/9/2012 2
Loch Ness Orthopedist 13/1/2011 2
创建表并插入脚本:
create table InsuranceCompanies (
cid int,
cname varchar(20),
primary key (cid)
);
create table Patient (
pid int,
pname varchar(20),
age int,
cid int,
gender char,
primary key (pid),
constraint foreign key (cid)
references InsuranceCompanies (cid)
);
create table Doctors (
did int ,
dname varchar(20),
speciality varchar(20),
age int,
cid int,
primary key (did),
constraint foreign key (cid)
references InsuranceCompanies (cid)
);
create table Visits(
vid int,
pid int,
did int,
date varchar(20),
primary key (vid),
constraint foreign key (pid)
references Patient (pid) ,
constraint foreign key (did)
references Doctors (did)
);
INSERT INTO InsuranceCompanies(cid, cname) VALUES
( 1111, 'Harel Inc' ),
( 2222, 'Clalit Inc' );
INSERT INTO Doctors ( did, dname, speciality, age, cid) VALUES
( 100, 'Jhonny Depp', 'Heart', 42, 1111 ),
( 101, 'Tom Tolan', 'Assholes', 62, 1111 ),
( 105, 'Yom Tov', 'Assholes', 52, 1111 ),
( 102, 'Lauren Jaime', 'Throat', 27, 2222 ),
( 103, 'Gomez Flaurence', 'Legs', 37, 2222 ),
( 106, 'David Harpaz', 'Orthopedist', 37, 2222 ),
( 107, 'David Schwimmer', 'Orthopedist', 37, 2222 ),
( 108, 'Sammy Salut', 'Orthopedist', 37, 1111 );
INSERT INTO Patient ( pid, pname, age, cid,gender) VALUES
( 200, 'Jon Gilmour', 25, 2222, 'm' ),
( 206, 'Bon Gilmour', 30, 2222, 'm' ),
( 205, 'Jon Gilmour', 22, 2222, 'm' ),
( 201, 'Bon Jovy', 21, 2222, 'm' ),
( 202, 'Loch Ness', 17, 2222, 'f' ),
( 203, 'Lilach Sonin', 12, 1111, 'f' ),
( 209, 'Lilach Dba', 34, 1111, 'f' ),
( 210, 'Paulina Daf', 32, 1111, 'f' ),
( 204, 'Gerry Jalor', 23, 1111, 'm' ),
( 208, 'Jerrushalem Jalor', 23, 1111, 'm' );
INSERT INTO Visits ( vid, pid, did, date) VALUES
( 300, 204, 100, '12/12/2012' ),
( 301, 204, 101, '12/12/2012' ),
( 302, 204, 101, '02/01/2012' ),
( 303, 202, 101, '17/09/2012' ),
( 311, 202, 105, '17/09/2012' ),
( 304, 203, 102, '12/12/2011' ),
( 312, 202, 106, '13/06/2012' ),
( 314, 202, 107, '13/01/2011' ),
( 313, 202, 108, '13/01/2011' ),
( 305, 204, 102, '10/10/2011' ),
( 306, 201, 100, '12/01/2012' ),
( 316, 204, 108, '18/05/2012' ),
( 307, 202, 100, '12/07/2012' ),
( 315, 203, 108, '12/07/2012' ),
( 310, 204, 103, '10/04/2012' ),
( 308, 203, 102, '12/12/2011' ),
( 309, 200, 101, '12/12/2012' );