Is it an accepted pattern to use a common junction table for all N:M relations? - sql

I've seen several databases which implements many-many relations by using a generic common junction table. I've never found this pattern in any literature, I suppose it's an anti-pattern, but does it have a name?
The usual approach is of course to use a distinct junction table for EACH many-many relation, not to put all relations in a generic common/global table for all relations in the whole database.
Btw, the reason I think it's an anti-pattern (at least when using RDBMS) is that you cannot have referential integrity on foreign keys.

Related

in a relational database, can we have a table without any relation with the other tables?

in a relational database, can we have a table without any relation with the other tables?
Yes. The way relations are expressed are with foreign keys. If a table you generate has no Foreign keys, and no foreign keys in other tables point to this table, it has no relationships.
It can still be given a relationship later though so don't worry about shooting yourself in the foot.
Of course. Even you can create a table without fields.
Yes you can. Tables do not have to have any relation to each other. Relations can always be added through the use of foreign keys if you want to add them later.
I'm creating a company management database and I have a "Company_Expenses" table that I just need for summery reports on the Company's revenues. I can't think of anything this table might need to be connected to so it's just on it's own for now.
Your question belies a larger problem with your understanding of databases.
A relation is a set of tuples (a relation can be thought of as a table).
A tuple can be thought of as a row.
Relationship in English means connectedness and has nothing to do with relation from relational databases.
Both relation and relationship share word roots, but in database theory, these words/concepts do not have anything to do with each other.
The root of the word relation in database theory comes from math (see function vs relation).

Mapping a 1:1 relationship on a relational schema

If I have two entities and the relation between them is 1:1. Also the participation of each of them is total... What I should do in this case in order to represent the relationship between them in the relational schema?
If the 1:1 relationship with total participation is the only relationship between the two entities, you just merge them into a single relation. The choice of the primary key will be arbitrary (pick one of the PK of the original entities, while the other PK will be an alternate key).
If instead there are additional relationships between the two entities, which prevent the merge into a single relation, you can treat the entities as in a parent-child relationship, and the choice of where to put the foreign key is arbitrary.
In the relational model that's called a join depencency and it can be simply expressed as a constraint between two relations such that P(A) = P(B), where P(A) and P(B) are projections on relations A and B. Although it's easy to support in relational terms, unfortunately SQL makes it difficult or impossible to enforce join dependencies between different tables because standard SQL doesn't support the ability to update more than one table simultaneously. To implement in SQL you have to either combine them into one table or temporarily disable the constraint while the tables are updated.

Translating ER to SQL DDL

When I am translating an ER to SQL DDL I need to Create a table only for the entities or for the relations too?
Yes, you need to create tables for both entities and relationships. Also, keep in mind that you have to include foreign keys and link your tables
It depends what type of relationship you have. If it is many to many relationship then it must require a separate table for the relationship itself. Any way you can search on google ER diagram to relational database or look the text book on the relational model chapter of Modern database management sytem of author Hoffer.
You require a CREATE TABLE statement for each ENTITY.
Your relations ships are generally implemented as FOREIGN KEY CONSTRAINTS or FOREIGN KEY INDEXES between those tables.
Each entity becomes a table and each many to many relationship becomes a table.
Add the child columns (FK column) to the (child) tables also. When you create a N:M (many to many) relationship in for example DeZign for Databases, you see that an intersection table is create automatically. The columns which are added automatically are in first instance the columns of the primary key of both tables. You can see that in this video:
http://www.datanamic.com/support/vd-dez001.html

What is the best practise for relational database tables in mysql?

I know, there is a lot of info on mysql out there. But I was not really able to find an answer to this specific and actually simple question:
Let's say I have two tables:
USERS
(with many fields, e.g. name, street, email, etc.) and
GROUPS
(also with many fields)
The relation is (I guess?) 1:n, that is ONE user can be a member of MANY groups.
What I dis, is create another table, named USERS_GROUPS_REL. This table has only two fields:
us_id (unique key of table USERS) and
gr_id (unique key of table GROUPS)
In PHP I do a query with join.
Is this "best practice" or is there a better way?
Thankful for any hint!
Hi all,
thanks for your quick and helpful support. Knowing that I was on the right way builds up my mysql-self-confidence a little. :-)
As many commented, my example is not 1:n but many to many. Just as a quick sql-lesson: :-)
Are these the right terms?
1:n one to many
n:1 many to one
n:n many to many?
You have described a many-to-many relationship. Using that relationship, many USERs can be members of many GROUPS. For your purposes, this is indeed the correct way to go.
One-to-many and one-to-one relationships do not require the link or cross-reference table (USERS_GROUPS_REL).
You might find this tutorial useful:
http://www.tonymarston.net/php-mysql/many-to-many.html
It's quite the best case :)
Creating a compound predicate primary key in the relation table is the optimal solution:
ALTER TABLE USERS_GROUPS_REL ADD PRIMARY KEY(us_id, gr_id)
That would be the best practice.
You have two tables on either side of the join and a mapping table (or linker table, or whatever other terminology is out there) in the middle which handles the Many-to-Many relationship (A Group has many Users and a User can belong to many Groups).
To increase performance, you should make a composite key for the mapping table out of us_id and gr_id. You can also create an index on the inverse so that if you need to sort by gr_id, you get the performance benefit there too.
One user can belong to many groups, and one group contains many users, so it is a many-to-many relationship.
The way you describe it is a typical and correct one. A many-to-many relationship is often mapped with an association class or relation table.
Sometimes the relation table has more columns. For example, a user may be the administrator of a particular group. The users_group_rel table would then also have a field administrator.

Subtyping database tables

I hear a lot about subtyping tables when designing a database, and I'm fully aware of the theory behind them. However, I have never actually seen table subtyping in action. How can you create subtypes of tables? I am using MS Access, and I'm looking for a way of doing it in SQL as well as through the GUI (Access 2003).
Cheers!
An easy example would be to have a Person table with a primary key and some columns in that table. Now you can create another table called Student that has a foreign key to the person table (its supertype). Now the student table has some columns which the supertype doesn't have like GPA, Major, etc. But the name, last name and such would be in the parent table. You can always access the student name back in the Person table through the foreign key in the Student table.
Anyways, just remember the following:
The hierarchy depicts relationship between supertypes and subtypes
Supertypes has common attributes
Subtypes have uniques attributes
Subtypes of tables is a conceptual thing in EER diagrams. I haven't seen an RDBMS (excluding object-relational DBMSs) that supports it directly. They are usually implemented in either
A set of nullable columns for each property of the subtype in a single table
With a table for base type properties and some other tables with at most one row per base table that will contain subtype properties
The notion of table sub-types is useful when using an ORM mapper to produce class sub-type heirarchy that exactly models the domain.
A sub-type table will have both a Foreign Key back to its parent which is also the sub-types table's primary key.
Keep in mind that in designing a bound application, as with an Access application, subtypes impose a heavy cost in terms of joins.
For instance, if you have a supertype table with three subtype tables and you need to display all three in a single form at once (and you need to show not just the supertype date), you end up with a choice of using three outer joins and Nz(), or you need a UNION ALL of three mutually exclusive SELECT statements (one for each subtype). Neither of these will be editable.
I was going to paste some SQL from the first major app where I worked with super/subtype tables, but looking at it, the SQL is so complicated it would just confuse people. That's not so much because my app was complicated, but it's because the nature of the problem is complex -- presenting the full set of data to the user, both super- and subtypes, is by its very nature complex. My conclusion from working with it was that I'd have been better off with only one subtype table.
That's not to say it's not useful in some circumstances, just that Access's bound forms don't necessarily make it easy to present this data to the user.
I have a similar problem I've been working on.
While looking for a repeatable pattern, I wanted to make sure I didn't abandon referential integrity, which meant that I wouldn't use a (TABLE_NAME, PK_ID) solution.
I finally settled on:
Base Type Table: CUSTOMER
Sub Type Tables: PERSON, BUSINESS, GOVT_ENTITY
I put nullable PRERSON_ID, BUSINESS_ID and GOVT_ENTITY_ID fields in CUSTOMER, with foreign keys on each, and a check constraint that only one is not null. It's easy to add new sub types, just need to add the nullable foreign key and modify the check constraint.