How do you resolve a many-to-many collection entity in a RDBMS? - primary-key

I'm trying to model artists and songs and I have a problem where I have a Song_Performance can be performed by many artists (say a duet) so I have an Artist_Group to represent who the songs is performed by.
Well, I now have a many-to-many relationship between Artist and Artist_Group, where an Artist_Group is uniquely identified by the collection of artists in that group. I can create an intersection entity that represents an Artist's participation in an Artist_Group (Artist_Group_Participation?)
I'm having trouble coming up with how to come up with a primary key for the Artist_Group entity that preserves the fact that the same set of artists represents the same group, and lacking a primary key for the Artist_Group entity means I'm lacking a foreign key for the Artist_Group_Participation entity.
The book "Mastering Data Modeling" by John Carlis and Joseph Maguire mention this shape and refer it to as a "Many-Many Collection Entity" and state that it is very rare, but doesn't state how to resolve it since obviously a many-to-many relationship can't be stored directly in a RDBMS. How do I go about representing this?
Edit:
Looks like everyone is suggesting an intersection table, but that's not my issue here. I have that. My issue is enforcing the constraint that you cannot add an Artist_Group entry where the group of artists that it contains are the same as an existing group, ignoring order. I thought about having the ID for Artist_Group be a varchar that is the concatenation of the various artists that comprise it, which would solve the issue if order mattered, but having an Artist_Group for "Elton John and Billy Joel" doesn't prevent the addition of a group for "Billy Joel and Elton John".

I guess I'm missing the point of the "Artist_Group" relation.
The data model in my mind is:
Artist: an individual person.
Song: The song itself.
Performance: A particular performance or arrangement of a song. Usually this would have one song, but you could provide an m:n linking table to accommodate a medley. Ideally, this would be a single real performance, i.e., there would be an associated date.
Recording: A particular fixed version of a performance (CD or whatever). Usually a Performance only has one Recording, but having a separate table would handle the Grateful Dead / multiple-bootleg scenario, as well as re-release albums, radio play vs. live vs. CD versions, etc.
Performance_Artists: A linking table from a particular performance to a list of performers. For each, you could also have an attribute that describes their role(s) in the performance (vocalist, drummer, etc.).
There's no explicit relationship between a set of performers, except that they share performances in common. Thus, any table that attempts to combine random sets of artists outside the context of a recording is not an accurate relational model, as there is no real relationship.
If you are trying to represent an explicit relationship between a set of artists (i.e., they are in the same band), well, bands have names that have uniqueness (though not enough to be a primary key), and a band could be stored simply as an Artist, and then have an Artist_Member linking table that is self-referencing back to the individual Artist records. Or you could have a separate Band table, and a Band_Members table to assign artists to it, perhaps with dates of membership. Either way, just remember that band members change over time and band roles change from one song to the next, so associating a band with a performance should not substitute for linking performances directly to the artists involved.

The primary key for both the Artist and Artist_Group would be an numeric, incremental ID. Then you'd have an Artist_Group_Participation table that has two columns: artist_id and group_id. These would be foreign keys that refer to the ID of their respective tables. Then to SELECT everything you'd use a JOIN.
EDIT: Sorry, I misunderstood your question. The only other way I can think of is add an "artists" column to your Artist_Group table that contains a serialized array (assuming you're using PHP, but other languages have equivalents) of the artists and their IDs. Then just add a UNIQUE constraint to the column.

You could make each artist's ID correspond to a bit in a bitfield. So if Elton John is ID 12 and Billy Joel is ID 123, then the "group" formed by a duet between Elton John and Billy Joel is Artist_Group ID 10633823966279326983230456482242760704 (i.e. it has the 12th and 123rd bit set).
You could enforce the relationship using the intersection table. For example, using a CHECK constraint in PostgreSQL:
CREATE TABLE Artist_Group_Participation (
artist_id int not null,
artist_group_id int not null,
PRIMARY KEY (artist_id, artist_group_id),
FOREIGN KEY (artist_id) REFERENCES Artists (artist_id),
FOREIGN KEY (artist_group_id) REFERENCES Artist_Group (artist_group_id),
CHECK (B'1'<<artist_id & artist_group_id <> 0)
);
Admittedly, this is a hack. It applies extra significance to the Artist_Group surrogate key, when surrogate keys are supposed to be unique but not contain information.
Also if you have thousands of artists, and new artists every day, things could get unwieldy because the length of the Artist_Group key's data type needs to grow larger all the time.

I guess you could build a primary key by sorting and concatenate the artist ids ??
group: 3,2,6 -> 2-3-6 and 6,3,2 -> 2-3-6

I don't have much experience in RDBMS. However, I have read papers of Codd and books by C.J. Date.
So, instead of using RDBMS jargon, I'll try to explain in more common sensical terms (at least to me!)
Here goes -
Singer names should be standard on "First Name - Last Name" basis
Each "Singer" should have an entry in the "Artists Group" table even if they have performed solo
Each entry in the "Artists Group" will consist of multiple "Singer" ordered alphabetically. There should be a single occurance of a specific combination.
Each song will have an entry of a unique record from "Artists Group" regardless of whether they are solo, duets or in a gang.
I don't know if this makes much sense, but it's my two cents!

Related

Adding an artificial primary key versus using a unique field [duplicate]

This question already has answers here:
Surrogate vs. natural/business keys [closed]
(19 answers)
Why would one consider using Surrogate keys vs Natural with ON UPDATE CASCADE?
(1 answer)
Closed 7 months ago.
Recently I Inherited a huge app from somebody who left the company.
This app used a SQL server DB .
Now the developer always defines an int base primary key on tables. for example even if Users table has a unique UserName field , he always added an integer identity primary key.
This is done for every table no matter if other fields could be unique and define primary key.
Do you see any benefits whatsoever on this? using UserName as primary key vs adding UserID(identify column) and set that as primary key?
I feel like I have to add add another element to my comments, which started to produce an essay of comments, so I think it is better that I post it all as an answer instead.
Sometimes there are domain specific reasons why a candidate key is not a good candidate for joins (maybe people change user names so often that the required cascades start causing performance problems). But another reason to add an ever-increasing surrogate is to make it the clustered index. A static and ever-increasing clustered index alleviates a high-cost IO operation known as a page split. So even with a good natural candidate key, it can be useful to add a surrogate and cluster on that. Read this for further details.
But if you add such a surrogate, recognise that the surrogate is purely internal, it is there for performance reasons only. It does not guarantee the integrity of your data. It has no meaning in the model, unless it becomes part of the model. For example, if you are generating invoice numbers as an identity column, and sending those values out into the real world (on invoice documents/emails/etc), then it's not a surrogate, it's part of the model. It can be meaningfully referenced by the customer who received the invoice, for example.
One final thing that is typically left out of this discussion is one particular aspect of join performance. It is often said that the primary key should also be narrow, because it can make joins more performant, as well as reducing the size of non-clustered indexes. And that's true.
But a natural primary key can eliminate the need for a join in the first place.
Let's put all this together with an example:
create table Countries
(
countryCode char(2) not null primary key clustered,
countryName varchar(64) not null
);
insert Countries values
('AU', 'Australia'),
('FR', 'France');
create table TourLocations
(
tourLocationName varchar(64) not null,
tourLocationId int identity(1,1) unique clustered,
countryCode char(2) not null foreign key references Countries(countryCode),
primary key (countryCode, tourLocationName)
);
insert TourLocations (TourLocationName, countryCode) values
('Bondi Beach', 'AU'),
('Eiffel Tower', 'FR')
I did not add a surrogate key to Countries, because there aren't many rows and we're not going to be constantly inserting new rows. I already know what all the countries are, and they don't change very often.
On the TourLocations table I have added an identity and clustered on it. There could be very many tour locations, changing all the time.
But I still must have a natural key on TourLocations. Otherwise I could insert the same tour location name with the same country twice. Sure, the Id's will be different. But the Id's don't mean anything. As far as any real human is concerned, two tour locations with the same name and country code are completely indistinguishable. Do you intend to have actual users using the system? Then you've got a problem.
By putting the same country and location name in twice I haven't created two facts in my database. I have created the same fact twice! No good. The natural key is necessary. In this sense The Impaler's answer is strictly, necessarily, wrong. You cannot not have a natural key. If the natural key can't be defined as anything other than "every meaningful column in the table" (that is to say, excluding the surrogate), so be it.
OK, now let's investigate the claim that an int identity key is advantageous because it helps with joins. Well, in this case my char(2) country code is narrower than an int would have been.
But even if it wasn't (maybe we think we can get away with a tinyint), those country codes are meaningful to real people, which means a lot of the time I don't have to do the join at all.
Suppose I gave the results of this query to my users:
select countryCode, tourLocationName
from TourLocations
order by 1, 2;
Very many people will not need me to provide the countries.countryName column for them to know which country is represented by the code in each of those rows. I don't have to do the join.
When you're dealing with a specific business domain that becomes even more likely. Meaningful codes are understood by the domain users. They often don't need to see the long description columns from the key table. So in many cases no join is required to give the users all of the information they need.
If I had foreign keyed to an identity surrogate I would have to do the join, because the identity surrogate doesn't mean anything to anyone.
You are talking about the difference between synthetic and natural keys.
In my [very] personal opinion, I would recommend to always use synthetic keys (and always call it id). The main problem is that natural keys are never unique; they are unique in theory, yes, but in the real world there are a myriad of unexpected and inexorable events that will make this false.
In database design:
Natural keys correspond to values present in the domain model. For example, UserName, SSN, VIN can be considered natural keys.
Synthetic keys are values not present in the domain model. They are just numeric/string/UUID values that have no relationship with the actual data. They only serve as a unique identifiers for the rows.
I would say, stick to synthetic keys and sleep well at night. You never know what the Marketing Department will come up with on Monday, and suddenly "the username is not unique anymore".
Yes having a dedicated int is a good thing for PK use.
you may have multiple alternate keys, that's ok too.
two great reasons for it:
it is performant
it protects against key mutation ( editing a name etc. )
A username or any such unique field that holds meaningful data is subject to changes. A name may have been misspelled or you might want to edit a name to choose a better one, etc. etc.
Primary keys are used to identify records and, in conjunction with foreign keys, to connect records in different tables. They should never change. Therefore, it is better to use a meaningless int field as primary key.
By meaningless I mean that apart from being the primary key it has no meaning to the users.
An int identity column has other advantages over a text field as primary key.
It is generated by the database engine and is guaranteed to be unique in multi-user scenarios.
it is faster than a text column.
Text can have leading spaces, hidden characters and other oddities.
There are multiple kinds of text data types, multiple character sets and culture dependent behaviors resulting in text comparisons not always working as expected.
int primary keys generated in ascending order have a superior performance in conjunction with clustered primary keys (which is a SQL-Server specialty).
Note that I am talking from a database point of view. In the user interface, users will prefer identifying entries by name or e-mail address, etc.
But commands like SELECT, INSERT, UPDATE or DELETE will always identify records by the primary key.
This subject - quite much like gulivar travels and wars being fought over which end of the egg you supposed to crack open to eat.
However, using the SAME "id" name for all tables, and autonumber? Yes, it is LONG establihsed choice.
There are of course MANY different views on this subject, and many advantages and disavantages.
Regardless of which choice one perfers (or even needs), this is a long established concept in our industry. In fact SharePoint tables use "ID" and autonumber by defualt. So does ms-access, and there probably more that do this.
The simple concpet?
You can build your tables with the PK and child tables with forighen keys.
At that point you setup your relationships between the tables.
Now, you might decide to add say some invoice number or whatever. Rules might mean that such invoice number is not duplicated.
But, WHY do we care of you have some "user" name, or some "invoice" number or whatever. Why should that fact effect your relational database model?
You mean I don't have a user name, or don't have a invoice number, and the whole database and relatonships don't work anymore? We don't care!!!!
The concept of data, even required fields, or even a column having to be unique ?
That has ZERO to do with a working relational data model.
And maybe you decide that invoice number is not generated until say sent to the customer. So, the fact of some user name, invoice number or whatever? Don't care - you can have all kinds of business rules for those numbers, but they have ZERO do to do with the fact that you designed a working relational data model based on so called "surrogate" or sometime called synthetic keys.
So, once you build that data model - even with JUST the PK "id" and FK (forighen keys), you are NOW free to start adding columns and define what type of data you going to put in each table. but, what you shove into each table has ZERO to do with that working related data model. They are to be thought as seperate concpets.
So, if you have a user name - add that column to the table. If you don't want users name, remove the column. As such data you store in the table has ZERO to do with the automatic PK ID you using - it not really any different then say what area of memory the computer going to allocate to load that data. Basic data operations of the system is has nothing to do with having build database with relationships that simple exist. And the data columns you add after having built those relationships is up to you - but will not, and should not effect the operation of the database and relationships you built and setup. Not only are these two concepts separate, but they free the developer from having to worry about the part that maintains the relationships as opposed to data column you add to such tables to store user data.
I mean, in json data, xml? We often have a master + child table relationship. We don't care how that relationship is maintained - but only that it exists.
Thus yes, all tables have that pk "ID". Even better? in code, you NEVER have to guess what the PK id is - it always the same!!!
So, data and columns you put and toss into a table? Those columns and data have zero to do with the PK id, and while it is the database generating that PK? It could be a web service call to some monkeys living in a far away jungle eating banana's and they give you a PK value based on how many bananas they eaten. We just really don't' care about that number - it is just internal house keeping numbers - one that we don't see or even care about in most code. And thus the number one rule to such auto matic PK values?
You NEVER give that auto PK number any meaning from a user and applcation point of view.
In summary:
Yes, using a PK called "id" for all tables? Common, and in fact in SharePoint and many systems, it not only the default, but is in fact required for such systems to operate.
Its better to use userid. User table is referenced by many other tables.
The referenced table would contain the primary key of the user table as foreign key.
Its better to use userid since its integer value,
it takes less space than string values of username and
the searches by the database engine would be faster
user(userid, username, name)
comments(commentid, comment, userid) would be better than
comments(commentid, comment, username)

How to resolve multiple values in one column in a table?

I have been tasked with designing a database from a scenario. However, while designing my solution I found I would have multiple values in one cell. We were told this is a repeating group and should be avoided in a database.
I get the repeating groups when I want to link the songs on an album to the album they are found on. For instance, there can be one or many songs on an album. However, a song could be on one or many albums (Dean Martin - Silver Bells could be on a Christmas Hits album and a Dean Martin album).
If I reference each song to its album I would use the AlbumId as a foreign key. However, if it was in multiple albums then I would have multiple AlbumId's as the foreign key. This gives me a repeating group as there will be multiple Ids in the same cell.
If this was reversed by storing all the album's songs on the Album entity I would have the same issue as the SongId would be a foreign key and each album will have multiple SongId's in the same cell.
The design I have includes these following entities:
song
and
album
The song entity will contain the following attribute types:
SongId (PK)
SongDuration
AlbumId (FK)
AudioFileSize
AudioFile
SongTitle
SongLyrics
SongNotes
The album entity will contain the following attribute types:
AlbumId (PK)
AlbumTitle
NumOfTracks
ReleaseDate
ProductionLabel (FK) //Goes to another table that has no issues.
AlbumCoverImage
CoverImageStory
AmountOfCDs
I am quite new to database design and I feel I have grasped it well. However, I am puzzled on how to solve this.
If any more information on the database is required I will happily provide it.
Any help is greatly appreciated.
Best regards,
Steve.
You have a many-to-many relationship. So, you can use a junction/association table:
create table songAlbums (
. . .,
songId int references songs(songId),
albumId int references albums(albumId),
. . .
)
You might want to include other information, such as the position on the album. Such a table could have a composite primary key (songId, albumId) or a synthetic primary key (generated always as identity).
We were told this is a repeating group and should be avoided in a database.
Not "avoided", but modelled, solved. Each column must be Atomic:
1NF: no multiple or compound values
2NF: no repeating groups
The simple solution is to model the multiple values in a subordinate table. In this case, with two Identifers Song and Album, an Associative table.
RecordID
That is the first and foremost error. It cripples both the modelling exercise, and the resulting "database".
The Relational Model requires:
the Key must be "made up from the data"
(ie. not an manufactured ID; GUID; UUID; etc, none of which are data)
each row (as distinct from a record with a RecordId) in each table must be unique
Data uniqueness cannot be obtained from a ID; GUID; UUID; etc. Further, the stupid thing is always an additional column and index.
That needs to be corrected.
Third, you have some columns in the wrong tables.
Album Data Model
Modelling is substantially cheaper than trying SQL. See if this satisfies the requirement.
Rather than going back-and-forth bringing you up to speed with Relational Databases, I have fixed up all issues. Eg. you have multiple CDs per Album, but that was not handled or requested, it must be resolved.
Also available in PDF.
It is rendered in IDEF1X, the Standard for modelling a Relational Database. You may find the short Introduction to IDEF1X helpful.

How To Interpret This Diagram

I am in a database course this semester and I'm trying to figure out how to interpret this diagram
I know the key symbols represent either a primary or foreign key, but I can't tell which ones are which. I think the tables that have the 2 perpendicular lines have at least one foreign key from the table where the line came from, but I am not 100% sure. That's about all I (think) I understand.
What I really need is someone to either tell me the name of this type of diagram and/or how to interpret it so that I can write the SQL script to represent it.
A Key symbol mean Primary Key or PK.
Foreign Key (FK) doesn't have any symbol but you can guess. For example student.dept_name is FK from department.dept_name
The arrow go from department to student mean one department have 0 to N students
They are two symbols starting the line one with a circle and another one doble lines. My guess one is 0 .. N and the other 1 .. N but without know how you make that diagram can't be sure.
This diagram is call ER or Entity Relationship
Each box is a table or Entity you have to create in your script, then create PK, and than define FK.
This is what I'm seeing in the diagram, although it may not be perfect because not all the keys have their direct lines to their primary sources. The >O or O< indicates there are required to be many of whatever it's against. An example is there are many students in a department. The O| or |O indicates there must be 1 and only 1. Each student must be registered with a department, but they can only be registered with one department. The || indicates a one to many plurality. Each course can have one or many sections (typically determined by how many students wish to attend that course).
For the issue of the keys, there is no apparent distinction between primary and foreign keys. I would assume that in each case, if a key is simply called ID or includes part of the table name (such as department: dept_name), then it is the primary key and all others are foreign keys. Again, somewhat difficult to tell since not all relationships are mapped in this particular diagram (such as teaches/takes and the key set course_id, semester, & year), but in these cases we assume that it's a composite key (values in multiple fields make up a unique record) rather than a single primary key (although there appears to be a single primary key in the section table). In such cases, simply saying section 01 or 01O doesn't mean anything and will likely return as many rows as there are class titles with a section number equivalent to those. You would have to specify course_id = CIT261, sec_id = '01O', semester = 'fall', year = 2015 for the first section of an online CIT261 course during the current semester, which should return a single row.
Another interesting note, it would appear that the advisor table satisfies a many to many relationship, and does not contain a primary key, but another composite key, but it doesn't seem to be a solid model as academic advisors are generally tied to the student via the department. This may be meant to reflect the instructors' TA.
I hope this points you in the right direction.
-C§

How to model the association of CDs with Genres?

I'm creating a database design for a web site that sells music CDs, and I've hit a brick wall because I can't get my head around whether the relationship between an CD and it's Genre's is one-to-many or many-to-many
Each CD can have multiple genres. For example "Ministry of Sound Dubstep Anthems" could have genres such as Dubstep, Dance and Electro.
The more I think about it though, each genre can also be linked to a number of CD's.
The way I have my Database at the moment is:
cd_table
PK ID
FK Genre
Description
...
genre_table
PK ID
Genre
If it was a many-to-many am I right in thinking I will need a join table such as:
cd_genre
CD_ID
Genre_ID
And then have them both acting as a Primary Key? How would I link the cd_genre to the cd_table? Or do I just remove the FK in cd_table, and then do a join when querying the CD's?
You're correct - the relationship between CD and Genre is many-to-many, for exactly the reasons you provide.
And yes, a cross-reference/join table like you describe is what you need.
Interestingly, depending on other constraints, you might want to be able to put genre in other places, too. For instance, song: an artist like Weird Al may put several different genres of songs on one of his albums, and the album itself doesn't necessarily have any single 'main' genre (but often have some 'theme').
I think you answered your own question. CD's and Genres are many-to-many, and you accomplish it with that two column table with the two foreign keys, usually referred to as a "join table." It's generally not necessary to think of that table as having a primary key, but rationally the two columns together are a composite primary key.
To determine multiplicity, ask the same question starting with the different relations:
Can a CD belong to many Genres?
Can a Genre contain more than one CD?
Of course, this is may be the wrong database model. Instead, Song<->Genre and Song<->CD, is the higher Normalized Form. It is a higher NF because CD<->Genre can be composed from CD<->Song<->Genre but CD<->Genre cannot answer the same queries about Songs on the CD (unless a CD can be at most one Genre).
On the other hand, one might only care about CDs and not Songs .. in which case modeling Songs irrelevant or even harmful excessive data. Likewise, perfect classification might overcomplicate practical classification - be aware of the tradeoffs between granularity of information and the use to the problem domain.

Difference between one-to-many and many-to-one relationship

What is the real difference between one-to-many and many-to-one relationship? It is only reversed, kind of?
I can't find any 'good-and-easy-to-understand' tutorial about this topic other than this one: SQL for Beginners: Part 3 - Database Relationships
Yes, it is vice versa. It depends on which side of the relationship the entity is present on.
For example, if one department can employ several employees then department to employee is a one-to-many relationship (1 department employs many employees), while employee to department relationship is many-to-one (many employees work in one department).
More info on the relationship types:
Database Relationships - IBM DB2 documentation
From this page about Database Terminology
Most relations between tables are one-to-many.
Example:
One area can be the habitat of many readers.
One reader can have many subscriptions.
One newspaper can have many subscriptions.
A Many to One relation is the same as one-to-many, but from a different viewpoint.
Many readers live in one area.
Many subscriptions can be of one and the same reader.
Many subscriptions are for one and the same newspaper.
What is the real difference between one-to-many and many-to-one relationship?
There are conceptual differences between these terms that should help you visualize the data and also possible differences in the generated schema that should be fully understood. Mostly the difference is one of perspective though.
In a one-to-many relationship, the local table has one row that may be associated with many rows in another table. In the example from SQL for beginners, one Customer may be associated to many Orders.
In the opposite many-to-one relationship, the local table may have many rows that are associated with one row in another table. In our example, many Orders may be associated to one Customer. This conceptual difference is important for mental representation.
In addition, the schema which supports the relationship may be represented differently in the Customer and Order tables. For example, if the customer has columns id and name:
id,name
1,Bill Smith
2,Jim Kenshaw
Then for a Order to be associated with a Customer, many SQL implementations add to the Order table a column which stores the id of the associated Customer (in this schema customer_id:
id,date,amount,customer_id
10,20160620,12.34,1
11,20160620,7.58,1
12,20160621,158.01,2
In the above data rows, if we look at the customer_id id column, we see that Bill Smith (customer-id #1) has 2 orders associated with him: one for $12.34 and one for $7.58. Jim Kenshaw (customer-id #2) has only 1 order for $158.01.
What is important to realize is that typically the one-to-many relationship doesn't actually add any columns to the table that is the "one". The Customer has no extra columns which describe the relationship with Order. In fact the Customer might also have a one-to-many relationship with ShippingAddress and SalesCall tables and yet have no additional columns added to the Customer table.
However, for a many-to-one relationship to be described, often an id column is added to the "many" table which is a foreign-key to the "one" table -- in this case a customer_id column is added to the Order. To associated order #10 for $12.34 to Bill Smith, we assign the customer_id column to Bill Smith's id 1.
However, it is also possible for there to be another table that describes the Customer and Order relationship, so that no additional fields need to be added to the Order table. Instead of adding a customer_id field to the Order table, there could be Customer_Order table that contains keys for both the Customer and Order.
customer_id,order_id
1,10
1,11
2,12
In this case, the one-to-many and many-to-one is all conceptual since there are no schema changes between them. Which mechanism depends on your schema and SQL implementation.
Hope this helps.
SQL
In SQL, there is only one kind of relationship, it is called a Reference. (Your front end may do helpful or confusing things [such as in some of the Answers], but that is a different story.)
A Foreign Key in one table (the referencing table)
References
a Primary Key in another table (the referenced table)
In SQL terms, Bar references Foo
Not the other way around
CREATE TABLE Foo (
Foo CHAR(10) NOT NULL, -- primary key
Name CHAR(30) NOT NULL
CONSTRAINT PK -- constraint name
PRIMARY KEY (Foo) -- pk
)
CREATE TABLE Bar (
Bar CHAR(10) NOT NULL, -- primary key
Foo CHAR(10) NOT NULL, -- foreign key to Foo
Name CHAR(30) NOT NULL
CONSTRAINT PK -- constraint name
PRIMARY KEY (Bar), -- pk
CONSTRAINT Foo_HasMany_Bars -- constraint name
FOREIGN KEY (Foo) -- fk in (this) referencing table
REFERENCES Foo(Foo) -- pk in referenced table
)
Since Foo.Foo is a Primary Key, it is unique, there is only one row for any given value of Foo
Since Bar.Foo is a Reference, a Foreign Key, and there is no unique index on it, there can be many rows for any given value of Foo
Therefore the relation Foo::Bar is one-to-many
Now you can perceive (look at) the relation the other way around, Bar::Foo is many-to-one
But do not let that confuse you: for any one Bar row, there is just one Foo row that it References
In SQL, that is all we have. That is all that is necessary.
What is the real difference between one to many and many to one relationship?
There is only one relation, therefore there is no difference. Perception (from one "end" or the other "end") or reading it backwards, does not change the relation.
Cardinality
Cardinality is declared first in the data model, which means Logical and Physical (the intent), and then in the implementation (the intent realised).
One to zero-to-many
In SQL that (the above) is all that is required.
One to one-to-many
You need a Transaction to enforce the one in the Referencing table.
One to zero-to-one
You need in Bar:
CONSTRAINT AK -- constraint name
UNIQUE (Foo) -- unique column, which makes it an Alternate Key
One to one
You need a Transaction to enforce the one in the Referencing table.
Many-to-Many
There is no such thing at the Physical level (recall, there is only one type of relation in SQL).
At the early Logical levels during the modelling exercise, it is convenient to draw such a relation. Before the model gets close to implementation, it had better be elevated to using only things that can exist. Such a relation is resolved by implementing an Associative Table at the physical [DDL] level.
There is no difference. It's just a matter of language and preference as to which way round you state the relationship.
Answer to your first question is : both are similar,
Answer to your second question is: one-to-many --> a MAN(MAN table) may have more than one wife(WOMEN table) many-to-one --> more than one women have married one MAN.
Now if you want to relate this relation with two tables MAN and WOMEN, one MAN table row may have many relations with rows in the WOMEN table. hope it clear.
One-to-Many and Many-to-One are similar in Multiplicity but not Aspect (i.e. Directionality).
The mapping of Associations between entity classes and the Relationships between tables. There are two categories of Relationships:
Multiplicity (ER term: cardinality)
One-to-one relationships (abbreviated 1:1): Example Husband and Wife
One-to-Many relationships (abbreviated 1:N): Example Mother and Children
Many-to-Many relationships (abbreviated M:N): Example Student and Subject
Directionality : Not affect on mapping but makes difference on how we can access data.
Uni-directional relationships: A relationship field or property that refers to the other entity.
Bi-directional relationships: Each entity has a relationship field or property that refers to the other entity.
This is an excellent question, according to my experience, in ERD diagrams and relational databases direction is implied. In RDBMS you always define Many-To->One (trivial case One-To->One) relationships. The Many side of the relationship, a.k.a children, references the One side, a.k.a parent and you implement this with a Foreign Key constraint. Technically speaking you have to access an index, fetch the Primary Key record of the One side and then visit this record to get more information.
You cannot do this the other way around unless we are speaking about Object-Relational DBMS such as Postgres, Intersystems Cache, etc. These DBMS allow you to define a bi-directional relationship between the two entities (tables). In that case accessing records the other way around, i.e. One--To-->Many is achieved by using an array of references (children). In ORMs you have classes that reference each other the same way we described here.
WARNING: Most RDBMS in the IT market are NOT relational database management systems in the strict sense, think about null values, duplicate records etc, many of these allowed features break the definition of what a Relation is.
There's no practical difference. Just use the relationship which makes the most sense given the way you see your problem as Devendra illustrated.
One-to-many and Many-to-one relationship is talking about the same logical relationship, eg an Owner may have many Homes, but a Home can only have one Owner.
So in this example Owner is the One, and Homes are the Many.
Each Home always has an owner_id (eg the Foreign Key) as an extra column.
The difference in implementation between these two, is which table defines the relationship.
In One-to-Many, the Owner is where the relationship is defined. Eg, owner1.homes lists all the homes with owner1's owner_id
In Many-to-One, the Home is where the relationship is defined. Eg, home1.owner lists owner1's owner_id.
I dont actually know in what instance you would implement the many-to-one arrangement, because it seems a bit redundant as you already know the owner_id. Perhaps its related to cleanness of deletions and changes.
---One to Many--- A Parent can have two or more children.
---Many to one--- Those 3 children can have a single Parent
Both are similar. This can be used according to the need. If you want to find children for a particular parent, then you can go with One-To-Many. Or else, want to find parents for twins, you may go with Many-To-One.
The easiest explanation I can give for this relationship is by piggybacking on evendra D. Chavan'sanswer.
Using the department and employee relationship
A department can have multiple employees, so from the employee side, it's one-to-many relationship, and from the department side it's many-to-one relationship
But if an employee can also belong to more than one department, we can also say from the employee side it's now many as opposed to one, so the relationship becomes many-to-many
In order words, a simple understanding would be, we can state that a relationship is many-to-many if one-to-many can be viewed from both sides
that is if;
one employee can belong to many departments (one-to-many)
one department can have many employees (one-to-many)
I am new to SQL and only have experience using SQLAlchemy. The documentation on relationships in SQLAlchemy does a good job explaining this, in my opinion.
You may find some clarity by reading this part
Also, I had to come up with my own example to think through this. I'll try to explain without writing a bunch of code for simplicity.
table Vehicle
column (name)
table Manufacturer
column (name)
A Vehicle can only have One manufacturer (Ford, Tesla, BMW etc.)
Manufacturers can make many Vehicles
Ford
Ford makes Mustang
Ford makes F-150
Ford makes Focus
Tesla
Tesla makes Model S
Tesla makes Model X
Tesla makes Roadster
When looking at the database rows you will want to decide if you want a column that references the other side of the relationship. This is where the SQLAlchemy documentation brings in the difference between backref vs. back_populates. I understand that is the difference between having a column in the table to reference the other side of the relationship or not having a column to reference the other side.
I hope this helps, and even more so, I hope I am accurate in the way I learned and understand this.
I have read most of the answer. The problem is not the relationship here at all. If you look at One to Many or Many to One conceptually, it is just a reversible relationship. HOWEVER, while implementing the concept in your software or application it differs a lot.
In case of Many to One, we often desire the table that has Many aspect to be written first and we desire it to associate with the table containing One aspect. If you convert Many to One concept into One to Many, you will have hard time writing the One aspect table first in your code. Since, the relationship is defined while you engineer the database, Many aspect table will seek for the One aspect table data for integrity. So if you are planning to do it by using foreign key -> unique key or foreign key -> primary key, Many to One implementation will be different even if you consider it as a One to Many.
I personally make associations without using actual relationship concepts in many cases. There is no such boundaries as to use Database concept to form relationship every time. Just make sure that your database integrity is maintained as you want, it is indexed properly for your search needs and is decently normalized.
one-to-many has parent class contains n number of childrens so it is a collection mapping.
many-to-one has n number of childrens contains one parent so it is a object mapping