Database design for patients and diseases [closed] - sql

Closed. This question needs to be more focused. It is not currently accepting answers.
Want to improve this question? Update the question so it focuses on one problem only by editing this post.
Closed 6 years ago.
Improve this question
I am creating an application (desktop) to store and retrieve patients' records along with diseases. As patients and diseases have a many to many relationship, so I've created three tables; PATIENTS, DISEASES and one is Junction table. As one patient can register more than once in a single disease over the time so 'PATIENTS' table contains composite primary key of patient's 'reference no' and 'registration date'. Table 'DISEASES' only contains 'name' as a primary key.
Now I am a little confused about the design of junction table. It is containing the composite primary key of 'PATIENTS' table and a primary key of 'DISEASES' table as foreign keys.
Should I make composite primary key of all these foreign keys in junction table or create another primary key or something different?
Any help would be greatly appreciated.

It doesn't seem like that design is quite right. If the patient's reference number uniquely identifies the patient, then that should be the primary key. If the same patient can register for a given disease multiple times, then that should be part of the key in the junction table, not in the patient table.
The primary key in the junction table should be what uniquely identifies an association, which in this case should be a composite key composed of the key from the patient table, the disease table, and the registration date.

I would suggest you one more table for cases. This table would contain an entry date. You should not use the disease name as primary key. This would make it difficult to correct typos or simply to choose a more appropriate name in the future, or maybe you would want to have a Latin as well as an English name.
Patient table
-------------
PK PatientID
Name
DateOfBirth
etc.
Disease table
-------------
PK DiseaseID
Name
Case table
-------------
PK CaseID
FK PatientID
EntryDate
etc.
CaseDisease table
-------------
PK, FK CaseID
PK, FK DiseaseID
Now you have these relations
Patient --1:n--> Case --1:n--> CaseDisease <--n:1-- Disease
EDIT:
The case table might not be necessary for now and might seem to be over-designed. However, should it turn out in future, that you have to store other data to a case as well; the db design would not have to be changed fundamentally.
UPDATE:
Alternatively, you could do it without a case table. In that case, the junction table would have a date as part of the primary key
PatientDisease table
-------------
PK, FK PatientID
PK, FK DiseaseID
PK Date
The relations would be
Patient --1:n--> PatientDisease <--n:1-- Disease

'name' as a primary key is not a good idea - there shoud be an Id column in that table which should be set as primary key
DiseasesToPatients table should be made of both foreign keys - from Patients and Diseases tables and they should be set as composite primary key on that table.

Related

One Primary Key Value in many tables

This may seem like a simple question, but I am stumped:
I have created a database about cars (in Oracle SQL developer). I have amongst other tables a table called: Manufacturer and a table called Parentcompany.
Since some manufacturers are owned by bigger corporations, I will also show them in my database.
The parentcompany table is the "parent table" and the Manufacturer table the "child table".
for both I have created columns, each having their own Primary Key.
For some reason, when I inserted the values for my columns, I was able to use the same value for the primary key of Manufacturer and Parentcompany
The column: ManufacturerID is primary Key of Manufacturer. The value for this is: 'MBE'
The column: ParentcompanyID is primary key of Parentcompany. The value for this is 'MBE'
Both have the same value. Do I have a problem with the thinking logic?
Or do I just not understand how primary keys work?
Does a primary key only need to be unique in a table, and not the database?
I would appreciate it if someone shed light on the situation.
A primary key is unique for each table.
Have a look at this tutorial: SQL - Primary key
A primary key is a field in a table which uniquely identifies each
row/record in a database table. Primary keys must contain unique
values. A primary key column cannot have NULL values.
A table can have only one primary key, which may consist of single or
multiple fields. When multiple fields are used as a primary key, they
are called a composite key.
If a table has a primary key defined on any field(s), then you cannot
have two records having the same value of that field(s).
Primary key is table-unique. You can use same value of PI for every separate table in DB. Actually that often happens as PI often incremental number representing ID of a row: 1,2,3,4...
For your case more common implementation would be to have hierarchical table called Company, which would have fields: company_name and parent_company_name. In case company has a parent, in field parent_company_name it would have some value from field company_name.
There are several reasons why the same value in two different PKs might work out with no problems. In your case, it seems to flow naturally from the semantics of the data.
A row in the Manufacturers table and a row in the ParentCompany table both appear to refer to the same thing, namely a company. In that case, giving a company the same id in both tables is not only possible, but actually useful. It represents a 1 to 1 correspondence between manufacturers and parent companies without adding extra columns to serve as FKs.
Thanks for the quick answers!
I think I know what to do now. I will create a general company table, in which all companies will be stored. Then I will create, as I go along specific company tables like Manufacturer and parent company that reference a certain company in the company table.
To clarify, the only column I would put into the sub-company tables is a column with a foreign key referencing a column of the company table, yes?
For the primary key, I was just confused, because I hear so much about the key needing to be unique, and can't have the same value as another. So then this condition only goes for tables, not the whole database. Thanks for the clarification!

SQL Creating New Table that is based of a column in an already created table

Here is an example of what I need, different values:
I already have table 1 created in the database.
Table 1: Person
Columns: PK->ID, Name, Favorite Color, Favorite Sport, etc..
This table is already in database and filled with values.
Now I want to create a second table, Table 2 which has a primary key of Favorite Sport column from my Table 1 and just one more column for the description.
Ex:
Table 2: Sports
Columns: Pk->Favorite Sport, description
I want to make sure I am just creating this table correctly, so I don't mess anything up. Would this be the correct syntax to use? (I will fill up the data separately after table is created.)
CREATE TABLE Sports (
Favorite_Sport Varcher(25),
Description Varcher(100),
PRIMARY KEY(Favorite_Sport),
Foreign KEY(Favorite_Sport) REFERENCES Person;
)
Thanks!
There are probably several ways to do this, but I think I'd go with
CREATE TABLE Sports
(SPORT Varchar2(25)
CONSTRAINT PK_SPORTS
PRIMARY KEY
USING INDEX,
Description Varchar2(100));
(I changed the name of the primary key column on the SPORTS table to SPORT).
You really don't want nor can you have SPORTS.SPORT reference PERSON.FAVORITE_SPORT, as FAVORITE_SPORT is not a primary or unique key on PERSON. Instead, you want the foreign key relationship to go the other way around, with PERSON.FAVORITE_SPORT referencing SPORTS.SPORT:
ALTER TABLE PERSON
ADD CONSTRAINT PERSON_FK1
FOREIGN KEY (FAVORITE_SPORT) REFERENCES SPORTS(SPORT);
SQLFiddle here
Best of luck.

Database Design Correct Practice

I've come across a small issue that probably pretty common, but that I've no idea how to search for. For example, say we have a database with the following tables:
Table of Exams - ExamID, Name
Table of Exam Questions - ExamID, QuestionID, Name
Should I make QuestionIDs be unique? I could make them unique for every ExamID, or I could just make QuestionIDs never repeat. Are there any advantages/disadvantages to doing either? Also, what should the primary keys be in both scenarios?
Kind of depends.
There are a lot of possibilities with no real "right" and "wrong".
My thoughts would be to probably separate it out into another table, so that the question could be reused across exams
Exam
----
ExamId int primary key,
Name varchar(500)
Questions
----
QuestionId int primary key,
Text varchar(500)
ExamQuestions
----
Id int primary key, -- this is optional, i just like "simple" primary keys rather than composite.
ExamId int FK, -- potentially create a unique constraint on examId/questionId
QuestionId int FK, -- potentially create a unique constraint on examId/questionId
questionOrder int -- this would allow a "ordering" of exam questions on a per exam basis.
Make ExamId as unique , because An Exam would not repeat again and again, but Question can repeat in the every exam.
Example : Term End Exam 2014 will not happen again in the next year , same question of Normalization may ask again and again.
If a question belongs exclusively to one exam you would make it unique for that exam. If you expect to see the question on different exams then it can't be dependent on the exam for uniqueness, it would get its key values generated independently of the exam.
An example of a case where an ID would be unique only for another entity would be an order/line item relationship, where a customer places an order that can have multiple line items. The line item has no meaning apart from the order that it belongs to, so you could identify the line items by an order id and a line item number that started from 0 for each order.
The important question isn't whether or not question ID should be unique. The important question is, "What are the semantics of the relationship between Exam and Question?" The answer to that tells us what the primary key of the question table should be.
Your Question table has a foreign key relationship with the Exam table that identifies the [one] exam to which a question belongs. It is the nature of that relationship that matters.
A non-identifying relationship is one in which the dependent entity (Question, in this case) can exist independently of the related "parent" entity (Table, in this case). One indication of this is whether a Question can be moved from one Exam to another, or if a Question need not belong to an Exam at all. If so, the primary key of the Question table should be simply the question id itself, which should therefore be unique and non-nullable.
Whether the Exam ID is nullable or not is dependent on the cardinality of the relationship
from Question to Exam: is it one-to-one (non-nullable) or zero-to-one (nullable).
An identifying relationship is one in which the dependent entity (Question) exists only within the context of the related "parent" entity (Table). If so, the primary key of the Question table should be compound, incorporating the Exam ID (foreign key to the Exam table) as well as the Question ID, with both Exam ID and Question ID non-nullable.
This constrains the Question ID to be unique within the scope of an Exam ID: whether it is
unique across the entire table or not doesn't really matter much at this point, since you need
the Exam ID and the Question ID to identify a particular question.
There are 2 tables
Exams - ExamID, Name to store exam information.
Exam Questions - ExamID, QuestionID, Name to store questions information with a foreign key from Exams table
This means that you are trying to represent a one to many relationship between Exams and Exam Questions tables meaning that a Exam has many Questions but a Question belongs to one and only one Exam.
If this is correct then make QuestionIDs primary Key in the Exam Questions table.
If this is not correct and a Exam has many Questions and Question belongs to many Exams then it is a many to many relationship. In this case you should have another Junction table for the many to many relationship. This the three tables would be
Exams - ExamID, Name to store exam information with ExamID as primary key
Exam Questions - QuestionID, Name to store questions information with QuestionID as primary key
Exam Questions Relationship - ExamID, QuestionID to represent the many to many relationship with a foreign key from Exams table and a foreign key from Exams Questions table

SQL: can many to many relationship have a PK in addition to the FKs from the other entities

I'm having problem in inserting the values of an exam in the DB, and the reason is that every question that have been taking in the exam need to be unique which is not the case, we want the system to allow us to duplicate questions in the 60 question exam. what can I do to make this happened?
Exam (ExamID, Student.UID, ExamFB, Evaluated, ExamLevel)
Primary key (ExamID)
Foreign Key (Student.UID)
Contains (ExamID, QID, X, Y, StdAnswer, CorrectAnswer, QuestionFB)
Primary key (ExamID, QID)
Question (QID, SecID, Supervisor.UID, QBody, LawID)
Primary key (QID)
Foreign key (SecID, Supervisor.UID)
Yes, a many to many junction table does not have to be unique, although in your scenario I imagine it should be, I don't see why you would have the same question more than once on an exam, however it is quite a common scenario, to pick a slightly different scenario, imagine a service history of a car, you might have a table of mechanics, and a table of cars, and a table to store each service:
Mechanics - MechanicID (PK) Name
Cars - CarID (PK), RegistrationNumber, Make, Model
It is possible that the same mechanic will service the same car more than once, so you can't make the primary key (CarID, MechanicID), so you would either need to just assign a surrogate primary key to the service table:
Services - ServiceID (PK), CarID (FK), MechanicID(FK), ServiceDate
Or add an additional column to your table that will make the composite key unique, e.g in the above make the key (CarID, MechanicID, ServiceDate).
In your case you could have an additional column QuestionNumber (1 - 60 in your case) that identifies where the question appears in your exam, then your PK would just be (ExamID, QuestionNumber), and keep the foreign key to QuestionID.
So your database diagram would look something like one of the below:
Add an IDENTITY Attribute with the FKs together will be your PK

SQL Foreign Key Redundancy

This is a question about foreign key redundancy
redundant foreign key? <- Similar Question
In General:
A Foreign Key from TABLE C references a Primary Key from Table B
A Foreign Key From Table C references a Primary Key from Table A
A Foreign Key from Table B references a Primary Key from Table A
Is the Foreign Key from C -> A necessary since C is connected through B to A?
Specific: 3 tables
Supplier Info Table A
Supplier ID - PK
Person Contact Info (for supplier) Table B
Part # - PK
Date Received - PK
Supplier ID - FK
Part Rprt Table C
Part # - PK & FK
Date - PK & FK
Supplier ID - FK
Thanks - Suggestions for reworking all the table are also welcome
The key would technically be redundant if you assume that the supplier for a person is always the supplier represented by the part. Remember, that things can change over time. Presumably, suppliers could merge, persons could change the supplier they are associated with, and the supplier associated with a part could change.
The data structure, however, does not look properly normalized. I would think that you would want a person table with information only about the person. I don't get the relationship between parts and persons.
So, I think you should rework your data structure. I would suggest that you start with the entities you have identified -- suppliers, persons, and parts. Then create association tables for them, if necessary. It is quite possible that each person should just have a SupplierId and each part should have a SupplierId and that models the relationships. If there is a relationship between parts and persons, then you might be able to satisfy that with just a PersonId field in parts.