1

我有表格Visit,其中包含 , 等列VisitID,还有PatientIDcolumn 。在表中有列和(它们一起是我的主键)。一个处方可以有很多药物,所以会有类似的东西:DoctorIDPrescriptionIDPrescriptionPrescriptionIDDrugID

处方ID:1 DrugID:38
处方ID:1 DrugID:278
处方ID:1 DrugID:7

Visit表中将插入“1”值作为PrescriptionID。但是现在我不能用外键加入这两个表,因为不是每次访问都有处方,所以PrescriptionID可以为空,我有错误,列必须是主键或必须是唯一的。我怎样才能以另一种方式加入这些表?

4

3 回答 3

2

您似乎在这里谈论两个不同的问题。

一个问题是,您希望在引用列中允许空值。这很简单,您只需要将列定义为可为空作为外键。该键应该引用的是另一个问题,这将我们引向我在您的问题中可以看到的两个问题中的另一个。

关于列必须是主键或唯一的错误与引用表使用单个列来引用复合(由两列组成)键这一事实有关。而且您不能仅引用键的一部分,因为引用必须指向特定的单行,并且您的Visit.PrescriptionID值可能会引用多个(这是正确的,因为引用表中的行并不是真正的处方,但处方项目)。这就是为什么告诉您该列必须是主键或唯一的原因。

因此,我建议按如下方式更改您的架构:

  1. 让您的Prescription表仅包含作为实体的处方。即使除了键之外没有其他属性,也让它存储在自己的表中:

    CREATE TABLE Presciption (
      PrescriptionID int
        IDENTITY  /* just an assumption */
        CONSTRAINT PK_Prescription PRIMARY KEY
    );
    
  2. 您现在的Prescription表格应该重命名为PrescriptionItemor PrescriptionDrug,遵循您的单数名词命名约定。它的PrescriptionID列将是一个外键引用Prescription.PrescriptionID,如下所示:

    CREATE TABLE PresciptionDrug (
      PrescriptionID int NOT NULL
        CONSTRAINT FK_PrescriptionDrug_Prescription
        FOREIGN KEY REFERENCING Prescription (PrescriptionID),
      DrugID int NOT NULL
        CONSTRAINT FK_PrescriptionDrug_Drug
        FOREIGN KEY REFERENCING Drug (DrugID),
      CONSTRAINT PK_PrescriptionDrug
        PRIMARY KEY (PrescriptionID, DrugID)
    );
    
  3. 现在你可以Visit.PrescriptionID像这样定义foreignon:

    ALTER TABLE Visit
    ADD CONSTRAINT FK_Visit_Prescription
        FOREIGN KEY REFERENCING Prescription (PrescriptionID)
    ;
    

    如果您想为就诊提供可选的处方,请不要忘记确保该列可以为空。(可空外键在 SQL Server 中非常好。)

于 2012-08-18T23:24:21.747 回答
1

我认为表结构应该是

Visit (VisitID, Time, .....) --no prescriptionID
Prescription (PrescriptionID, ..... , VisitID) --VisitID as FK
PrescriptionDrugs(PrescriptionID, DrugID) -- Both columns as PK

那么您的查询将是

SELECT v.VisitID FROM Visit v
LEFT JOIN Prescription p ON v.VisitID = p.VisitID
LEFT JOIN PrescriptionDrugs pd ON p.PrescriptionID = pd.PrescriptionID

那会给你类似的东西

VisitID        PrescriptionID      DrugID
101            ABC                 Anti-Bio
101            ABC                 Asprin
102            BAC                 Anti-Bio

意思是 2 种药物Visit 101和 1 种药物Visit 102

无论如何,使用您当前的架构,试试这个

select v.visitid, v.presid, p.drugid 
from visit v 
left join prescription p on v.presid = p.presid
于 2012-08-18T20:55:24.277 回答
0

你问怎么做:

select *
  from Visit as V left outer join
    Prescription as P on P.PrescriptionId = V.PrescriptionId

这将返回所有访问和任何适用的处方。没有处方的访问将导致没有处方数据的输出行。

于 2012-08-18T20:56:17.063 回答