How to use the foreign key in SQL Server - sql-server

I have following question: let's say we have a Chen-Notation 1:n and m:n.
So 1 has a primary key and n also, where do I type the foreign key ? in the n ?
And the second question is about m:n, both have a primary key, and I need 1 more table because it's m:n, do I type the both primary keys as foreign keys in the 3rd table?

Example of a 1:n relationship : customers and orders
One customer may have several orders. In this situation, you want a column in the orders table with a foreign key that references the primary key of the customers table.
Sample DDL:
create table customers (
id int primary key,
name varchar(50),
email varchar(50)
);
create table orders (
id int primary key
price float,
customer_id int foreign key references customer(id)
);
Example of a n:m relationship : books and authors
A book may be written by more than one author. An author may have written more than one book. You create a bridge table, also called junction table, called books_authors, to represent that relationship, and that contains foreign keys to the two other tables.
Sample:
create table books (
id int primary key,
name varchar(50)
);
create table authors (
id int primary key,
name varchar(50)
);
create table books_authors(
book_id int foreign key references books(id),
author_id int foreign key references authors(id),
constraint pk_books_authors primary key(book_id, author_id)
);

So 1 has a primary key and n also, where do I type the foreign key ? in the n ?
The foreign key lives in the n, because 1 can have many keys, but you can't have a field that holds multiple values, you need to have one value per field, so it's in the n.
And the second question is about m:n, both have a primary key, and I need 1 more table because it's m:n, do I type the both primary keys as foreign keys in the 3rd table?
Yes, because that 3rd table in effect has a many-to-one relationship to both tables.

Related

Is it better to have an Id as primary key or a double foreign key

I want to know what is the most optimized data structure:
I have 2 tables like:
CREATE TABLE Person
(
Id Int NOT NULL PRIMARY KEY,
name varchar(50)
)
CREATE TABLE Group
(
Id Int NOT NULL PRIMARY KEY,
nameOfGroup varchar(50)
)
In my table to connect persons to groups I want to know what is the most optimized way to create it between an ID and then the foreign keys, like that:
CREATE TABLE PersonGroup
(
Id Int DISTINCT NOT NULL PRIMARY KEY,
PersonId Int, -- which is a foreign key to table Person
GroupId Int -- which is a foreign key to table Group
)
OR having the 2 foreign keys as a primary because no one can be 2 times in the same group anyway, like that :
CREATE TABLE PersonGroup
(
PersonId Int NOT NULL, -- which is a foreign key to table Person
GroupId Int NOT NULL, -- which is a foreign key to table Group
CONSTRAINT PK_PersonSgroup PRIMARY KEY (PersonId, GroupId)
)
What is the most optimized between those 2 tables for querying after (if there is more optimize).
Thank you to have read my post.
The first solution (PK identity) is incomplete because you need to have an alternate (or surrogate) key (AK) compound of the two FK.
In the two possibilities, you must know that the order of the two FK in the PK or the AK is very important. This order must follow the usual querying way. So the questions are
do you use first the group then the person in queries ?
do you use first the personthen the group in queries ?
Also you need an index on the second PK, not the first of the PK or AK compound of the two PK.
For me the best table will be:
CREATE TABLE PersonGroup
(
PersonId Int NOT NULL REFERENCES Person (PersonId),
GroupId Int NOT NULL REFERENCES Group (GroupId),
CONSTRAINT PK_PersonSgroup PRIMARY KEY (PersonId, GroupId)
);
CREATE INDEX X_PersonGroup_FK_Group (GroupId);

PrImary key or foreign key for a m-to-n relation table

I have a table in my database that models a m-to-n relation. The primary key of this relation is of course the combined primary keys of the 2 entities involved in this relation.
The relation goes like this: m customers have n orders
create table customer(
cid SERIAL PRIMARY KEY,
...
);
create table order(
oid SERIAL PRIMARY KEY,
...
);
create table has(
oid INTEGER REFERENCES order(oid) ON DELETE CASCADE,
cid INTEGER REFERENCES customer(cid) ON DELETE CASCADE,
FOREIGN KEY (oid,cid) or PRIMARY KEY (oid,cid)
);
I'm a bit confused on what to use here: primary key or foreign key to put them in relation?
thanks in advance for any help.
Jaiel
You should be using PRIMARY KEY for the composite key in table has. The combination of the order and customer IDs in the has table is a primary key in that table, because it allows the identification of a unique single record.
Note that both oid and cid in table has are foreign keys, pointing to the order and customer tables, respectively.

Are foreign keys that are part of a composite key automatically indexed in Oracle?

For instance, if I have a students table:
CREATE TABLE student (
student_id NUMBER(8),
student_name VARCHAR2(30),
CONSTRAINT pk_student PRIMARY KEY (student_id)
);
And a subject table:
CREATE TABLE subject (
subject_id NUMBER(8),
subject_name VARCHAR2(30),
CONSTRAINT pk_subject PRIMARY KEY (subject_id)
);
And then I create a third table of student's favorites subjects:
CREATE TABLE fav_sub (
student_id NUMBER(8),
subject_it NUMBER(8),
CONSTRAINT pk_fav_sub PRIMARY KEY (student_id, subject_id),
CONSTRAINT fk_1_fav_sub FOREIGN KEY (student_id) REFERENCES student(student_id),
CONSTRAINT fk_2_fav_sub FOREIGN KEY (subject_id) REFERENCES subject(subject_id)
);
Do I then need to manually create indexes for the foreign keys in the fav_sub table such as:
CREATE INDEX in_1_fav_sub ON fav_sub(student_id);
CREATE INDEX in_2_fav_sub ON fav_sub(subject_id);
Or are the indexes for the foreign keys automatically created by the database, since they're part of the composite key?
Edit: Just to clarify, I'm not asking if an index for a foreign key is automatically created, I'm asking if an index for a foreign key is created WHEN it's part of a composite key, since Oracle automatically indexes primary keys.
The creation of the primary key indexes the combination of [student_id, subject_id]. Adding foreign key constraints to each individual column does not create an index on them, and if you want it (which is probably a good idea), you'd have to manually create it.

what is "both sides of a relationship must have the same number of column" error?

hello I have nine tables in database Two of the tables in the database are:
tbl_unit
--------
Unit_Number(pk),
Floor_Number(pk),
Apartment_plaque(pk),
BedRoom_Count,
BathRoom_Count,
Rental_Fees_Unit,
Unit_Area,
Unit_state
and
tbl_payment
-----------
Renter_National_Code(pk),
Apartment_Plaque(pk),
Floor_Number(pk),
Unit_Number(pk),
Owner_National_Code,
Payment_Date,
Debt,
Other_Amounts,
Other_amounts_comment,
amount_of_payment
I can't determine the none of primary key's in tbl_payment as foreign key for primary key's in tbl_unit and i recieve "both sides of a relationship must have the same number of columns" error
What's the problem?
A table can have only one primary key. Your tbl_payment table has a composite primary key consisting of 4 columns while the tbl_unit table has a composite primary key of 3 columns.
I believe you want a foreign key on the tbl_payment table to relate a payment to a specific unit. In that case, add a 3-column foreign key on tbl_payment referencing the primary key of tbl_units:
ALTER TABLE dbo.tbl_payment
ADD CONSTRAINT fk_tbl_payment_tbl_unit
FOREIGN KEY (
Unit_Number
, Floor_Number
, Apartment_plaque
)
REFERENCES dbo.tbl_unit(
Unit_Number
, Floor_Number
, Apartment_plaque
);

Primary and Foreign Key at the same time

Would it be possible in SQL Server 2008 to have a table created with 2 columns that are at the same time primary and foreign keys? If yes, how would such a code look like? I've searched and came up with nothing.
Sure, no problem:
CREATE TABLE dbo.[User]
(
Id int NOT NULL IDENTITY PRIMARY KEY,
Name nvarchar(1024) NOT NULL
);
CREATE TABLE [Group]
(
Id int NOT NULL IDENTITY PRIMARY KEY,
Name nvarchar(1024) NOT NULL
);
CREATE TABLE [UserToGroup]
(
UserId int NOT NULL,
GroupId int NOT NULL,
PRIMARY KEY CLUSTERED ( UserId, GroupId ),
FOREIGN KEY ( UserId ) REFERENCES [User] ( Id ) ON UPDATE NO ACTION ON DELETE CASCADE,
FOREIGN KEY ( GroupId ) REFERENCES [Group] ( Id ) ON UPDATE NO ACTION ON DELETE CASCADE
);
This is quite commonly used to model many-to-many relations.
These are totally different constructs.
A Primary Key is used to enforce uniqueness within a table, and be a unique identifier for a certain record.
A Foreign Key is used for referential integrity, to make sure that a value exists in another table.
The Foreign key needs to reference the primary key in another table.
If you want to have a foreign key that is also unique, you could make a FK constraint and add a unique index/constraint to that same field.
For reference purposes, SQL Server allows a FK to refer to a UNIQUE CONSTRAINT as well as to a PRIMARY KEY field.
It is probably not a good idea since often you want to allow duplicate foreign keys in the table. Even if you don't now, in the future, you might, so best not to do this. See Is it fine to have foreign key as primary key?
Just a quick note - from Microsoft pages (http://msdn.microsoft.com/en-us/library/ms189049.aspx)...
"A foreign key constraint does not have to be linked only to a primary key constraint in another table; it can also be defined to reference the columns of a UNIQUE constraint in another table."
Not used often, but useful in some circumstances.

Resources